Skip to content

Commit

Permalink
[backend] refactor product conversion into BSSrcServer::Product
Browse files Browse the repository at this point in the history
  • Loading branch information
mlschroe committed Sep 8, 2016
1 parent 2d736f1 commit 08783aa
Show file tree
Hide file tree
Showing 2 changed files with 179 additions and 137 deletions.
168 changes: 168 additions & 0 deletions src/backend/BSSrcServer/Product.pm
@@ -0,0 +1,168 @@
# Copyright (c) 2016 SUSE LLC
#
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License version 2 as
# published by the Free Software Foundation.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program (see the file COPYING); if not, write to the
# Free Software Foundation, Inc.,
# 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
#
package BSSrcServer::Product;

use strict;
use warnings;

use BSConfiguration;
use BSSrcServer::Link;
use BSUtil;
use BSRevision;
use BSSrcrep;
use BSXML;
use BSVerify;

my $projectsdir = "$BSConfig::bsdir/projects";
my $srcrep = "$BSConfig::bsdir/sources";
my $uploaddir = "$srcrep/:upload";

our $notify_repservers = sub {
};

# run the productconverter on _product to create/update/delete
# all _product:xxx packages
#
sub expandproduct {
my ($projid, $packid, $rev, $files, $user, $fail) = @_;

if (!$files) {
# gone!
my @packages = grep {/^\Q${packid}:\E/} BSRevision::lspackages_local($projid);
for my $opid (@packages) {
unlink("$projectsdir/$projid.pkg/$opid.upload-MD5SUMS");
unlink("$projectsdir/$projid.pkg/$opid.rev");
unlink("$projectsdir/$projid.pkg/$opid.mrev");
unlink("$projectsdir/$projid.pkg/$opid.xml");
$notify_repservers->('package', $projid, $opid);
}
return 1;
}
if ($files->{'_link'}) {
eval {
$files = BSSrcServer::Link::handlelinks({ %$rev, 'project' => $projid, 'package' => $packid }, $files);
die("$files\n") unless ref $files;
};
if ($@) {
die($@) if $fail;
return undef;
}
}
my $dir = "$uploaddir/expandproduct_$$";
BSUtil::cleandir($dir);
mkdir_p($dir);
for my $file (sort keys %$files) {
BSSrcrep::copyonefile_tmp($projid, $packid, $file, $files->{$file}, "$dir/$file");
}
my @prods = grep {/.product$/} sort keys %$files;
my %pids;
for my $prod (@prods) {
print "converting product $prod\n";
my $odir = "$dir/$prod.out";
my $olog = "$dir/$prod.logfile";
system('rm', '-rf', $odir) if -d $odir;
unlink($olog) if -e $olog;
mkdir_p($odir);
# run product converter and read stdout
my $pid;
if (!($pid = xfork())) {
delete $SIG{'__DIE__'};
open(STDOUT, '>>', $olog) || die("$olog: $!\n");
open(STDERR, '>&STDOUT');
$| = 1;
exec("./bs_productconvert", "$dir/$prod", $odir, $projid);
die("500 bs_productconvert: $!\n");
}
waitpid($pid, 0) == $pid || die("500 waitpid $pid: $!\n");
if ($?) {
my $s = readstr($olog);
$s =~ s/^\n+//s;
$s =~ s/\n+$//s;
warn("bs_productconvert failed: $?\n");
BSUtil::cleandir($dir);
rmdir($dir);
die("$s\n") if $fail;
return undef;
}
my @out = sort(ls($odir));
if (!@out) {
warn("bs_productconvert produced nothing\n");
BSUtil::cleandir($dir);
rmdir($dir);
return undef;
}
for my $p (@out) {
my $pdir = "$odir/$p";
my $pid = $p;
$pid =~ s/^_product[_:]//;
$pid =~ s/[:\000-\037]/_/sg;
$pid = "$packid:$pid";
$pids{$pid} = 1;
my %pfiles;
for my $pfile (sort(ls($pdir))) {
next if $pfile eq '_meta';
$pfiles{$pfile} = BSSrcrep::addfile($projid, $pid, "$pdir/$pfile", $pfile);
}
my $srcmd5 = BSSrcrep::addmeta($projid, $pid, \%pfiles);
my $oldrev = BSRevision::getrev_local($projid, $pid);
if ($oldrev && $oldrev->{'srcmd5'} eq $srcmd5 && $oldrev->{'rev'}) {
# we're lucky, no change
next;
}
my $prev = {'srcmd5' => $srcmd5, 'time' => time(), 'user' => $user, 'comment' => 'autogenerated', 'version' => '1', 'vrev' => '1'};
BSRevision::addrev_local({'vrev' => 1, 'nolinkinfodb' => 1}, $projid, $pid, $prev);
if (! -e "$projectsdir/$projid.pkg/$pid.xml") {
my $pidpack = readxml("$pdir/_meta", $BSXML::pack, 1);
if ($pidpack) {
eval {
$pidpack->{'name'} = $pid unless defined $pidpack->{'name'};
BSVerify::verify_pack($pidpack, $pid);
};
if ($@) {
warn($@);
undef $pidpack;
}
}
$pidpack ||= {
'name' => $pid,
'title' => $pid,
'description' => "autogenerated from $packid by source server",
};
# XXX no mrev files for product packages?
writexml("$projectsdir/$projid.pkg/.$pid.xml", "$projectsdir/$projid.pkg/$pid.xml", $pidpack, $BSXML::pack);
}
rmdir($pdir);
$notify_repservers->('package', $projid, $pid);
}
rmdir($odir);
}
BSUtil::cleandir($dir);
rmdir($dir);
# now do away with the old packages
my @packages = grep {/^\Q${packid}:\E/} BSRevision::lspackages_local($projid);
@packages = grep {!$pids{$_}} @packages;
for my $opid (@packages) {
unlink("$projectsdir/$projid.pkg/$opid.upload-MD5SUMS");
unlink("$projectsdir/$projid.pkg/$opid.rev");
unlink("$projectsdir/$projid.pkg/$opid.mrev");
unlink("$projectsdir/$projid.pkg/$opid.xml");
$notify_repservers->('package', $projid, $opid);
}
return 1;
}

1;
148 changes: 11 additions & 137 deletions src/backend/bs_srcserver
Expand Up @@ -70,8 +70,9 @@ use BSSrcServer::Access;
use BSSrcServer::Projlink;
use BSSrcServer::Link;
use BSSrcServer::Service;
use BSSrcServer::Product;

# configure projlink and link handling
# configure modules
$BSSrcServer::Projlink::getrev = \&getrev;
$BSSrcServer::Projlink::findpackages = \&findpackages;
$BSSrcServer::Projlink::readpackage = \&readpackage;
Expand All @@ -86,6 +87,8 @@ $BSSrcServer::Service::addrev = \&addrev;
$BSSrcServer::Service::notify = \&notify;
$BSSrcServer::Service::notify_repservers = \&notify_repservers;

$BSSrcServer::Product::notify_repservers = \&notify_repservers;

$Build::Rpm::unfilteredprereqs = 1 if defined $Build::Rpm::unfilteredprereqs;

use strict;
Expand Down Expand Up @@ -386,135 +389,6 @@ sub mergeservicerun {
return ($rev, $BSXML::revision);
}

#
# run the productconverter on _product to create/update/delete
# all _product:xxx packages
#
sub expandproduct {
my ($projid, $packid, $rev, $files, $user, $fail) = @_;

if (!$files) {
# gone!
my @packages = grep {/^\Q${packid}:\E/} BSRevision::lspackages_local($projid);
for my $opid (@packages) {
unlink("$projectsdir/$projid.pkg/$opid.upload-MD5SUMS");
unlink("$projectsdir/$projid.pkg/$opid.rev");
unlink("$projectsdir/$projid.pkg/$opid.xml");
notify_repservers('package', $projid, $opid);
}
return 1;
}
if ($files->{'_link'}) {
eval {
$files = BSSrcServer::Link::handlelinks({ %$rev, 'project' => $projid, 'package' => $packid }, $files);
die("$files\n") unless ref $files;
};
if ($@) {
die($@) if $fail;
return undef;
}
}
my $dir = "$uploaddir/expandproduct_$$";
BSUtil::cleandir($dir);
mkdir_p($dir);
for my $file (sort keys %$files) {
BSSrcrep::copyonefile_tmp($projid, $packid, $file, $files->{$file}, "$dir/$file");
}
my @prods = grep {/.product$/} sort keys %$files;
my %pids;
for my $prod (@prods) {
print "converting product $prod\n";
my $odir = "$dir/$prod.out";
my $olog = "$dir/$prod.logfile";
system('rm', '-rf', $odir) if -d $odir;
unlink($olog) if -e $olog;
mkdir_p($odir);
# run product converter and read stdout
my $pid;
if (!($pid = xfork())) {
delete $SIG{'__DIE__'};
open(STDOUT, '>>', $olog) || die("$olog: $!\n");
open(STDERR, '>&STDOUT');
$| = 1;
exec("./bs_productconvert", "$dir/$prod", $odir, $projid);
die("500 bs_productconvert: $!\n");
}
waitpid($pid, 0) == $pid || die("500 waitpid $pid: $!\n");
if ($?) {
my $s = readstr($olog);
$s =~ s/^\n+//s;
$s =~ s/\n+$//s;
warn("bs_productconvert failed: $?\n");
BSUtil::cleandir($dir);
rmdir($dir);
die("$s\n") if $fail;
return undef;
}
my @out = sort(ls($odir));
if (!@out) {
warn("bs_productconvert produced nothing\n");
BSUtil::cleandir($dir);
rmdir($dir);
return undef;
}
for my $p (@out) {
my $pdir = "$odir/$p";
my $pid = $p;
$pid =~ s/^_product[_:]//;
$pid =~ s/[:\000-\037]/_/sg;
$pid = "$packid:$pid";
$pids{$pid} = 1;
my %pfiles;
for my $pfile (sort(ls($pdir))) {
next if $pfile eq '_meta';
$pfiles{$pfile} = BSSrcrep::addfile($projid, $pid, "$pdir/$pfile", $pfile);
}
my $srcmd5 = BSSrcrep::addmeta($projid, $pid, \%pfiles);
my $oldrev = BSRevision::getrev_local($projid, $pid);
if ($oldrev && $oldrev->{'srcmd5'} eq $srcmd5 && $oldrev->{'rev'}) {
# we're lucky, no change
next;
}
my $prev = {'srcmd5' => $srcmd5, 'time' => time(), 'user' => $user, 'comment' => 'autogenerated', 'version' => '1', 'vrev' => '1'};
BSRevision::addrev_local({'vrev' => 1, 'nolinkinfodb' => 1}, $projid, $pid, $prev);
if (! -e "$projectsdir/$projid.pkg/$pid.xml") {
my $pidpack = readxml("$pdir/_meta", $BSXML::pack, 1);
if ($pidpack) {
eval {
$pidpack->{'name'} = $pid unless defined $pidpack->{'name'};
BSVerify::verify_pack($pidpack, $pid);
};
if ($@) {
warn($@);
undef $pidpack;
}
}
$pidpack ||= {
'name' => $pid,
'title' => $pid,
'description' => "autogenerated from $packid by source server",
};
writexml("$projectsdir/$projid.pkg/.$pid.xml", "$projectsdir/$projid.pkg/$pid.xml", $pidpack, $BSXML::pack);
}
rmdir($pdir);
notify_repservers('package', $projid, $pid);
}
rmdir($odir);
}
BSUtil::cleandir($dir);
rmdir($dir);
# now do away with the old packages
my @packages = grep {/^\Q${packid}:\E/} BSRevision::lspackages_local($projid);
@packages = grep {!$pids{$_}} @packages;
for my $opid (@packages) {
unlink("$projectsdir/$projid.pkg/$opid.upload-MD5SUMS");
unlink("$projectsdir/$projid.pkg/$opid.rev");
unlink("$projectsdir/$projid.pkg/$opid.xml");
notify_repservers('package', $projid, $opid);
}
return 1;
}

#
# return version and release of commit
#
Expand Down Expand Up @@ -714,7 +588,7 @@ sub addrev {
my $rev = {'srcmd5' => $srcmd5, 'time' => time(), 'user' => $user, 'comment' => $comment, 'requestid' => $requestid};

if ($packid eq '_product') {
expandproduct($projid, $packid, $rev, $files, $user, 1);
BSSrcServer::Product::expandproduct($projid, $packid, $rev, $files, $user, 1);
}

if ($packid ne '_project' && $packid ne '_pattern') {
Expand Down Expand Up @@ -2095,7 +1969,7 @@ sub delpackage {

# get rid of the generated product packages as well
if ($packid eq '_product') {
expandproduct($projid, $packid, undef, undef);
BSSrcServer::Product::expandproduct($projid, $packid, undef, undef);
}
notify_repservers('package', $projid, $packid);
notify("SRCSRV_DELETE_PACKAGE", { "project" => $projid, "package" => $packid, "sender" => ($cgi->{'user'} || "unknown"), "comment" => $cgi->{'comment'}, "requestid" => $cgi->{'requestid'} });
Expand All @@ -2116,7 +1990,7 @@ sub undeletepackage {
my $rev = BSRevision::getrev_local($projid, $packid);
if ($rev) {
my $files = BSSrcrep::lsrev($rev);
expandproduct($projid, $packid, $rev, $files, $rev->{'user'});
BSSrcServer::Product::expandproduct($projid, $packid, $rev, $files, $rev->{'user'});
}
}
notify_repservers('package', $projid, $packid);
Expand Down Expand Up @@ -2438,8 +2312,8 @@ sub getproductrepositories {
for my $product (@{$xml->{'products'}->{'product'}}) {
my @pr;
for my $repo (@{$product->{'register'}->{'updates'}->{'repository'}}) {
my @p = published_path(undef, $repo->{'project'}, $repo->{'name'});
my $path = { 'path' => $p[0]{'path'}, 'update' => undef };
my ($path) = published_path({}, $repo->{'project'}, $repo->{'name'});
$path = { 'path' => $path->{'path'}, 'update' => undef };
$path->{'arch'} = $repo->{'arch'} if $repo->{'arch'};
$path->{'zypp'} = $repo->{'zypp'} if $repo->{'zypp'};
$path->{'debug'} = undef if $repo->{'name'} =~ m/_debug$/;
Expand All @@ -2451,8 +2325,8 @@ sub getproductrepositories {
if (defined($repo->{'url'})) {
$path = { 'url' => $repo->{'url'} };
} else {
my @p = published_path({"medium" => $repo->{'medium'}}, $repo->{'project'}, $repo->{'name'});
$path = { 'path' => $p[0]{'path'} };
($path) = published_path({ 'medium' => $repo->{'medium'} }, $repo->{'project'}, $repo->{'name'});
$path = { 'path' => $path->{'path'} };
}
$path->{'arch'} = $repo->{'arch'} if $repo->{'arch'};
$path->{'zypp'} = $repo->{'zypp'} if $repo->{'zypp'};
Expand Down

0 comments on commit 08783aa

Please sign in to comment.