#!/usr/local/bin/perl5
# -*- perl -*-
use P4CGI ;
use strict ;
#
#####################################################################
##
## CONFIGURATION INFORMATION
## All config info should be in $configFile (see init() in P4CGI.pm)
##
#####################################################################
##
## Label Diff Viewer
##
#####################################################################
# Set back references
my $homepage="index.cgi";
my $backtohome="Back to Home" ;
# Define variables set by command arguments
my $label1 ; # Labels to diff
my $label2 ;
my $showSame ; # defined if files that are the same in both labels
# should be listed
my $showNotSame ; # defined if files that are not the same in both labels
# should be listed
my $showDiff ; # defined if files that exist in only one of the labels
# should be displayed
# Get arguments
$label1 = P4CGI::cgi()->param("LABEL1") ;
&P4CGI::bail("No first label specified") unless defined $label1 ;
$label2 = P4CGI::cgi()->param("LABEL2") ;
&P4CGI::bail("No second label specified") unless defined $label2 ;
$showSame = P4CGI::cgi()->param("SHOWSAME") ;
undef $showSame if $showSame ne "Y" ;
$showNotSame = P4CGI::cgi()->param("SHOWNOTSAME") ;
undef $showNotSame if $showNotSame ne "Y" ;
$showDiff = P4CGI::cgi()->param("SHOWDIFF") ;
undef $showDiff if $showDiff ne "Y" ;
# Print title and legend
print
"",
&P4CGI::start_page("Label Diff",
"",
$homepage,$backtohome) ;
# Define a typeglob for use as file handle
local *P4 ;
#
# Get basic data for labels
#
my ($date1,$time1,$owner1,$desc1,$opt1,$view1,@view1) = &getLabelData($label1) ;
my ($date2,$time2,$owner2,$desc2,$opt2,$view2,@view2) = &getLabelData($label2) ;
#
# Print basic label data
#
print
"",
&P4CGI::start_table("width=100%"),
&P4CGI::table_row(-type => "th",
-align => "center",
"$label1 vs.
$label2"),
&P4CGI::end_table();
print
"
" ;
# Start table
print
"",
&P4CGI::start_table(""),
&P4CGI::table_row(-type => "th",
-bgcolor=>"white",
"",$label1,$label2),
&P4CGI::table_row({-align => "right",
-text => "Date:"},
{-bgcolor => "white",
-text => "$time1 $date1"},
{-bgcolor => "white",
-text => "$time2 $date2"});
print
"",
&P4CGI::table_row({-align => "right",
-text => "Owner:"},
{-bgcolor => "white",
-text =>$owner1},
{-bgcolor => "white",
-text =>$owner2});
print
"",
&P4CGI::table_row({-align=>"right",
-valign=>"top",
-text=>"Description"},
{-bgcolor => "white",
-text =>$desc1},
{-bgcolor => "white",
-text =>$desc2});
if(( $opt1 ne "") or ( $opt2 ne "")) {
print
"",
&P4CGI::table_row({-align => "right",
-text => "Options:"},
{-bgcolor => "white",
-text =>$opt1},
{-bgcolor => "white",
-text =>$opt2});
}
print
"",
&P4CGI::table_row({-align => "right",
-valign=>"top",
-text => "View:"},
{-bgcolor => "white",
-text =>$view1},
{-bgcolor => "white",
-text =>$view2});
print
"",
&P4CGI::end_table(),
"
";
# Get files for labels
my (@lfiles1,@lfiles2);
my %files1 ;
my $v ;
my @tmp1 ;
foreach $v (@view1) {
&P4CGI::p4call(*P4, "files \"$v\@$label1\"" );
while() {
push @tmp1,$_ ;
$_ =~ s/\#(\d+).*// ; ;
$files1{$_} = $1 ;
}
close P4 ;
} ;
@lfiles1 = sort @tmp1 ;
my @tmp2 ;
my $commonFound=0 ;
my $commonAndSameRev=0 ;
foreach $v (@view2) {
&P4CGI::p4call(*P4, "files \"$v\@$label2\"" );
while() {
push @tmp2,$_ ;
$_ =~ s/\#(\d+).*// ;
my $otherRev = $files1{$_} ;
if(defined $otherRev) {
$commonFound++ ;
$commonAndSameRev++ if ($otherRev == $1) ;
}
}
close P4 ;
} ;
@lfiles2 = sort @tmp2 ;
my ($nfiles1,$nfiles2) ;
$nfiles1 = @lfiles1 ;
$nfiles2 = @lfiles2 ;
my $fileslisted = "Yes" ;
print
"Label $label1 has $nfiles1 files
",
"Label $label2 has $nfiles2 files
",
"The labels have $commonFound file", $commonFound==1?"":"s",
" in common $commonAndSameRev at the same revision
";
if($commonFound == 0) {
print
"",
"The two labels have no files in common - comparsion aborted." ;
}
else {
if(defined $showSame and defined $showNotSame and defined $showDiff) {
print "Files:
\n" ;
}
elsif(!defined $showSame and !defined $showNotSame and !defined $showDiff) {
print "Listed files are:
\n" ;
print " None\n" ;
$fileslisted = undef ;
}
else {
print "Listed files are:\n" ;
defined $showSame and do {
print " Files not modified (common file, common revision)\n";} ;
defined $showNotSame and do {
print " Modified files (common file, different revision)\n";} ;
defined $showDiff and do {
print " Files in only one of $label1
and $label2\n" ; } ;
print "\n" ;
} ;
# Print list of files
if(defined $fileslisted) {
print
"",
&P4CGI::start_table("border bgcolor=white"),
&P4CGI::table_row("-type","th",
"File",
"$label1
Revision",
undef,
" ",
"$label2
Revision") ;
my $f1 = shift @lfiles1 ;
my $f2 = shift @lfiles2 ;
while(defined $f1 or defined $f2) {
my ($name1,$rev1,$name2,$rev2) = ("",0,"",0) ;
if(defined $f1) {
$f1 =~ /^([^\#]+)\#(\d+)/ ;
$name1 = $1 ; $rev1 = $2 ;
}
if(defined $f2) {
$f2 =~ /^([^\#]+)\#(\d+)/ ;
$name2 = $1 ; $rev2 = $2 ;
}
if($name1 eq $name2) {
if((defined $showSame and ($rev1 == $rev2)) or
(defined $showNotSame and ($rev1 != $rev2))) {
if($rev1 == $rev2) {
print &P4CGI::table_row(&P4CGI::ahref("-url",
&P4CGI::FLV_URL(),
&P4CGI::fixspaces("FSPC=$name1"),"$name1"),
{-text => "$rev1",
-align => "center"},
undef,
" ",
{-text => "(same)",
-align => "center"}) ;
}
else {
print &P4CGI::table_row(&P4CGI::ahref("-url",
&P4CGI::FLV_URL(),
&P4CGI::fixspaces("FSPC=$name1"),"$name1"),
{-text=>&P4CGI::ahref("-url",&P4CGI::FV_URL(),
&P4CGI::fixspaces("FSPC=$name1"),
"REV=$rev1",
"$rev1"),
-align=>"center"},
undef,
{-text=>&P4CGI::ahref("-url",&P4CGI::FDV_URL(),
&P4CGI::fixspaces("FSPC=$name1"),
"REV=$rev1",
"REV2=$rev2",
"ACT=edit",
"<diff>"),
-align=>"center"},
{-text=>&P4CGI::ahref("-url",&P4CGI::FV_URL(),
&P4CGI::fixspaces("FSPC=$name1"),
"REV=$rev2",
"$rev2"),
-align=>"center"},) ;
}
}
if(defined $f1) { $f1 = shift @lfiles1 ;} ;
if(defined $f2) { $f2 = shift @lfiles2 ;} ;
}
elsif (($name2 ne "") and ($name1 eq "" or $name1 gt $name2)) {
if(defined $showDiff) {
print &P4CGI::table_row(&P4CGI::ahref(-url => &P4CGI::FLV_URL(),
&P4CGI::fixspaces("FSPC=$name2"),"$name2"),
{-text => "",
-align => "center",
-bgcolor => "red"},
undef,
" ",
{-text=>&P4CGI::ahref("-url",&P4CGI::FV_URL(),
&P4CGI::fixspaces("FSPC=$name1"),
"REV=$rev2",
"$rev2"),
-align=>"center"},) ;
}
$f2 = shift @lfiles2 if(defined $f2) ;
}
else {
if(defined $showDiff) {
print &P4CGI::table_row(&P4CGI::ahref("-url",
&P4CGI::FLV_URL(),
&P4CGI::fixspaces("FSPC=$name1"),"$name1"),
{-text=>&P4CGI::ahref("-url",&P4CGI::FV_URL(),
&P4CGI::fixspaces("FSPC=$name1"),
"REV=$rev1",
"$rev1"),
-align=>"center"},
undef,
" ",
{-text => "",
-align => "center",
-bgcolor => "red"}) ;
}
$f1 = shift @lfiles1 if(defined $f1) ;
}
}
print
"",
&P4CGI::end_table() ;
}
}
print &P4CGI::end_page() ;
###
### Subroutines
###
# Get label data.
# Returns list containing "Mod date","mod time","owner","description","view"
sub getLabelData($ ) {
my $label = shift @_ ;
local *P4 ;
my ($date,$time,$owner,$desc,$options,$view,@view) ;
# Mod. date, mod. time, owner, description, view
&P4CGI::p4call( *P4, "label -o $label" );
# Get label, time, date, owner
while() {
chop ;
$_ = P4CGI::fixSpecChar($_) ;
/^Label:\s+(\S+)/ && do { $label=$1 ; next ; } ;
/^Date:\s+(\S+)\s+(\S+)/ && do { $date=$1 ; $time=$2 ; next ; } ;
/^Owner:\s+(\S+)/ && do { $owner=$1 ; next ; } ;
/^Description:/ && do { last ;} ;
} ;
# Get description
while() {
chomp ;
s/^\s+// ;
next if /^\s*$/ ;
/^Options:\s*(.*)/ and do { $options = $1 ; next ; } ;
last if /^View:/ ;
if(defined $desc) {
$desc .= "
\n$_" ;
}
else {
$desc = $_ ;
}
} ;
# Get view
while() {
chomp ;
s/^\s+// ;
s/\s+$// ;
next if /^\s*$/ ;
push @view,$_ ;
if(defined $view) {
$view .= "
\n$_" ;
}
else {
$view = $_ ;
}
} ;
close P4 ;
return ($date,$time,$owner,
"$desc",$options,"$view",@view) ;
};