#!/usr/bin/perl

use RPM::Header;
use DBI;
require "config";

my $firstrun = undef;
my $transfer = undef;
my (@list, @flist, $dbh, @row, $row, $rpm, $sth, %oldS, %oldM, %hdr, %report, $size, $Ssize, $mail, $type, @vals);
my ($bMail, $bVersion, $srpm, $status);

if ($ARGV[0] eq "firstrun") {
	$firstrun = "true";
	print "Debug: Firstrun is on\n";
} 

foreach $repo (keys %repo_root) {
    @flist=(); # clear list of RPMs
    %old=();
    foreach (@srpm_root) {
	    if (($repo eq "orphaned") || ($repo eq "obsolete")) {
		$path=$repo_root{$repo};
	    }
	    else {
		$path=$repo_root{$repo} . $_;
	    }
	    if (-d $path) { # Not all of the srpm_root's dirs may be present in all repos
	    	print "Debug: path is=$path\n";
		opendir (DIR,$path) || die "cant open $_\n";
		@list = sort grep {/\.rpm$/} readdir(DIR);
		closedir(DIR);
    		foreach $rpm (@list) {
			$rpm = $path."/".$rpm;
		}
		push @flist, @list;
	    }
    }

    @flist = &deleteDup(\@flist);

    print "Begin to read ".($#flist+1)." srpms\n";

    $dbh = DBI->connect($dsn,$dbUser,$dbPass) || die "cant connect to mysql\n";

    unless ($firstrun) {
	$sth = $dbh->prepare("SELECT name, CONCAT(version,'-',rel) FROM srpm WHERE repo='$repo'");
	$sth->execute();
	while (@row = $sth->fetchrow_array){
	    $oldS{$row[0]} = $row[1];
	}

	$sth = $dbh->prepare("SELECT mail FROM maintainers");
	$sth->execute();
	while (@row = $sth->fetchrow_array){
	    $oldM{$row[0]} = 1;
	}
	
	$sth = $dbh->prepare("SELECT mail FROM teams");
	$sth->execute();
	while (@row = $sth->fetchrow_array){
	    $oldM{$row[0]} = 1;
	}
    }

    foreach $rpm (@flist){ 
	my $hdr =RPM::Header->new($rpm);
	unless ($hdr) {
		$report{"BAD_FILES"} .= "$rpm\tRPM::err\n";
		next;
	};
	
	if ($hdr->{"GROUP"} eq "") {
		$report{"BAD_GRP"} .= "$rpm\n";
		next;
	}

	$sth = $dbh->prepare("SELECT id from groups WHERE rpmgroup=? LIMIT 1");
	$sth->execute($hdr->{"GROUP"});
	$row = $sth->fetchrow_array;
	
	unless ($row) {
		$sth = $dbh->prepare("INSERT groups VALUES('',?)");
		$sth->execute($hdr->{"GROUP"});
		$sth = $dbh->prepare("SELECT LAST_INSERT_ID()");
		$sth->execute();
		$row = $sth->fetchrow_array();
	}

	($mail) = ($hdr->{"PACKAGER"} =~/<\s*([\w|\-]+)\s*[\@|at]/);
	$mail = lc($mail);
	unless (exists $oldM{$mail} || $repo ne "Sisyphus") {
		$type = ($hdr->{"PACKAGER"} =~ /packages/ ||
			$hdr->{"PACKAGER"} =~ /security/ )?"team":"man";

		$sth = $dbh->prepare("INSERT maintainers VALUES(?,?,?)");
		$sth->execute($mail,$hdr->{"PACKAGER"},$type);

		if ($type eq "man"){
			$sth = $dbh->prepare("INSERT members VALUES(?,?,?,?,?,?,?,?,?,?,?)");
			$sth->execute($mail,$hdr->{"PACKAGER"},'','','','','','','','','');
		} else {
			$sth = $dbh->prepare("INSERT teams VALUES(?,?,?,?)");
			$sth->execute($mail,$hdr->{"PACKAGER"},'','');
		}
		$report{"NEW_MAINTAINERS"} .= join("\t",$hdr->{"PACKAGER"},$type) . "\n" unless($firstrun);
		$oldM{$mail} = 1;
	}
	

	if (exists $oldS{$hdr->{'NAME'}} &&
		$oldS{$hdr->{'NAME'}} eq $hdr->{'VERSION'}."-".$hdr->{'RELEASE'}) {
		delete $oldS{$hdr->{'NAME'}};
		next;
	}
	else {
	    print "New SRPM: $hdr->{'NAME'} $hdr->{'VERSION'}."-".$hdr->{'RELEASE'}\n";
	}

	$size = (stat($rpm))[7];
	$Ssize += $size;
	
	# roBot found new srpm, so init new transfer
	unless ( $firstrun || $transfer) {
		if ($repo eq "Sisyphus") {
		    print "New transfer for Sisyphus\n";
		    $sth = $dbh->do("INSERT transfer VALUES('',NOW(),0,0)");
		    $sth = $dbh->prepare("SELECT LAST_INSERT_ID()");
		    $sth->execute();
		    $transfer = $sth->fetchrow_array();
		}
	}
	
	$sth = $dbh->prepare("REPLACE srpm VALUES(?,?,?,?,?,?,?,?,?,?,?,?,?)");
	$sth->execute(
		$hdr->{'NAME'}, $hdr->{'VERSION'},$hdr->{'RELEASE'},$hdr->{'SERIAL'},$row,$mail,
		&makeDateTime($hdr->{'BUILDTIME'}),$size,$hdr->{'SUMMARY'},
		$hdr->{'DESCRIPTION'},$hdr->{'URL'},$hdr->{'COPYRIGHT'}, $repo
	);

	if ($transfer) {
		unless (exists $oldS{$hdr->{'NAME'}}) {
			$status = "new";	
		} else {
			$status = "updated";
		}
		$sth = $dbh->prepare("REPLACE translist VALUES(?,?,?,?,?,?)");
		$sth->execute($transfer,$hdr->{'NAME'},$oldS{$hdr->{'NAME'}},$hdr->{'VERSION'}."-".$hdr->{'RELEASE'},$status,$repo);
		delete $oldS{$hdr->{'NAME'}} if (exists($oldS{$hdr->{'NAME'}}));
	}
	
	unless ($firstrun) {
		$sth = $dbh->prepare("SELECT name, version, time FROM changelogs WHERE rpm=? AND repo='$repo' GROUP BY rpm " .
			"HAVING time=MAX(time)");
		$sth->execute($hdr->{'NAME'});
		@row = $sth->fetchrow_array();

		unless ( grep { $row[0] eq $_ } @{$hdr->{'CHANGELOGNAME'}} ) {
			$report{'LOST_LAST_CHANGE'} .= join ("\t", $hdr->{'NAME'}, $hdr->{'VERSION'}."-".$hdr->{'RELEASE'},
				$row[1], $row[2]
			) . "\n";
		}

		$sth = $dbh->prepare("DELETE FROM changelogs WHERE rpm=? AND repo='$repo'");
		$sth->execute($hdr->{'NAME'});
	}
	
	$i = 0;
	foreach ( @{$hdr->{'CHANGELOGTIME'}} ) {
		$sth = $dbh->prepare("REPLACE changelogs VALUES(?,?,?,?,?,?,'$repo')");
		if ( @{$hdr->{'CHANGELOGNAME'}}[$i] =~ /altlinux/) {
			($bMail) = ( @{$hdr->{'CHANGELOGNAME'}}[$i] =~ /<\s*([\w|\-]+)\s*[\@|at]/ );
		} else {
			$bMail = undef;
		}
		($bVersion) = (@{$hdr->{'CHANGELOGNAME'}}[$i] =~ /([\w\-\.]+)\s*$/);
		@vals = ( &makeDate(@{$hdr->{'CHANGELOGTIME'}}[$i]), $bMail, $bVersion,
			@{$hdr->{'CHANGELOGNAME'}}[$i], @{$hdr->{'CHANGELOGTEXT'}}[$i] );
		$sth->execute($hdr->{'NAME'},@vals);
		$i++;
	}

    }

    next if ($firstrun);

    foreach $srpm (sort keys %oldS) {
	$sth = $dbh->prepare("DELETE FROM srpm WHERE name=? AND repo='$repo'");
	$sth->execute($srpm);
	$sth = $dbh->prepare("DELETE FROM rpm WHERE srpm=? AND repo='$repo'");
	$sth->execute($srpm);
	$report{"REMOVED_SRPMS"} .= $srpm."\n";

	unless ($transfer || $repo ne "Sisyphus") {
		$sth = $dbh->do("INSERT transfer VALUES('',NOW(),0,0)");
		$sth = $dbh->prepare("SELECT LAST_INSERT_ID()");
		$sth->execute();
		$transfer = $sth->fetchrow_array();
	}
	
	$sth = $dbh->prepare("INSERT translist VALUES(?,?,?,?,?,?)");
	$sth->execute($transfer,$srpm,$oldS{$srpm},undef,"deleted",$repo);
    }

    foreach $mail (sort keys %oldM){
	if (defined($oldM{$mail})) { next };
	print "We lost: $mail\n";
	$sth = $dbh->do('DELETE FROM members WHERE mail="'.$mail.'"');
	$sth = $dbh->do('DELETE FROM maintainers WHERE mail="'.$mail.'"');
	$report{"LOST_MAINTAINERS"} .= $mail."\n";
    }

    if ($transfer && $repo eq "Sisyphus"){
	$sth = $dbh->prepare("UPDATE transfer SET s_size=? WHERE tid=?");
	$sth->execute($Ssize,$transfer);
    }

    sub makeDateTime {
	my $time = shift;
	my @time = localtime($time);
	$time[5]+=1900; $time[4]++;
		return "$time[5]-$time[4]-$time[3] $time[2]:$time[1]:$time[0]";
    }

    sub makeDate {
	my $time = shift;
	my @time = localtime($time);
	$time[5]+=1900; $time[4]++;
	return "$time[5]-$time[4]-$time[3]";
    }

}
