package Hydra::Helper::AddBuilds;
use strict;
use warnings;
use utf8;
use Encode;
use JSON::MaybeXS;
use Nix::Store;
use Nix::Config;
use Hydra::Model::DB;
use Hydra::Helper::Nix;
use Digest::SHA qw(sha256_hex);
use File::Basename;
use File::stat;
use File::Path;
use File::Temp;
use File::Spec;
use Hydra::Helper::CatalystUtils;
our @ISA = qw(Exporter);
our @EXPORT = qw(
updateDeclarativeJobset
handleDeclarativeJobsetBuild
handleDeclarativeJobsetJson
);
sub updateDeclarativeJobset {
my ($db, $project, $jobsetName, $declSpec) = @_;
my @allowed_keys = qw(
enabled
hidden
type
flake
description
nixexprinput
nixexprpath
checkinterval
schedulingshares
enableemail
emailoverride
keepnr
);
my %update = ( name => $jobsetName );
foreach my $key (@allowed_keys) {
next unless defined $declSpec->{$key};
$update{$key} = $declSpec->{$key};
delete $declSpec->{$key};
}
if (defined $update{type}) {
if ($update{type} == 0) {
$update{flake} = undef;
} elsif ($update{type} == 1) {
$update{nixexprpath} = undef;
$update{nixexprinput} = undef;
}
}
$db->txn_do(sub {
my $jobset = $project->jobsets->update_or_create(\%update);
$jobset->jobsetinputs->delete;
foreach my $name (keys %{$declSpec->{"inputs"}}) {
my $data = $declSpec->{"inputs"}->{$name};
my $row = {
name => $name,
type => $data->{type}
};
$row->{emailresponsible} = $data->{emailresponsible} // 0;
my $input = $jobset->jobsetinputs->create($row);
$input->jobsetinputalts->create({altnr => 0, value => $data->{value}});
}
delete $declSpec->{"inputs"};
die "invalid keys ($declSpec) in declarative specification file\n" if (%{$declSpec});
});
};
sub handleDeclarativeJobsetJson {
my ($db, $project, $declSpec) = @_;
$db->txn_do(sub {
my @kept = keys %$declSpec;
push @kept, ".jobsets";
$project->jobsets->search({ name => { "not in" => \@kept } })->update({ enabled => 0, hidden => 1 });
foreach my $jobsetName (keys %$declSpec) {
my $spec = $declSpec->{$jobsetName};
eval {
updateDeclarativeJobset($db, $project, $jobsetName, $spec);
1;
} or do {
print STDERR "ERROR: failed to process declarative jobset ", $project->name, ":${jobsetName}, ", $@, "\n";
}
}
});
}
sub handleDeclarativeJobsetBuild {
my ($db, $project, $build) = @_;
eval {
my $id = $build->id;
die "Declarative jobset build $id failed" unless $build->buildstatus == 0;
my $declPath = ($build->buildoutputs)[0]->path;
my $declText = eval {
readNixFile($declPath)
} or do {
print STDERR "ERROR: failed to readNixFile $declPath: ", $@, "\n";
die;
};
my $declSpec = decode_json($declText);
handleDeclarativeJobsetJson($db, $project, $declSpec);
1;
} or do {
$project->jobsets->find({ name => ".jobsets" })->update({ errormsg => $@, errortime => time, fetcherrormsg => undef })
};
};
1;