2
0
mirror of https://github.com/xcat2/xcat-core.git synced 2026-05-17 11:54:16 +00:00

Merge pull request #7550 from VersatusHPC/fix/profile-asset-dotted-osvers

fix: handle dotted OS versions in profile asset lookup
This commit is contained in:
Markus Hilger
2026-05-06 19:18:26 +02:00
committed by GitHub
5 changed files with 369 additions and 59 deletions
+53 -24
View File
@@ -463,22 +463,22 @@ sub getsynclistfile()
none
Error:
Example:
xCAT::SvrUtils->get_os_search_list("ubuntu18.04.2");
Will returns
# ubuntu18.04.2
# ubuntu18.04.1
# ubuntu18.04.0
# ubuntu18.04
# ubuntu18.4
# ubuntu18.03
# ubuntu18.3
# ubuntu18.02
# ubuntu18.2
# ubuntu18.01
# ubuntu18.1
# ubuntu18.00
# ubuntu18.0
# ubuntu18
xCAT::SvrUtils->get_os_search_list("ubuntu24.04.1");
Will return
# ubuntu24.04.1
# ubuntu24.04.0
# ubuntu24.04
xCAT::SvrUtils->get_os_search_list("rocky9.6");
Will return
# rocky9.6
# rocky9.5
# rocky9.4
# rocky9.3
# rocky9.2
# rocky9.1
# rocky9.0
# rocky9
Comments:
none
@@ -491,8 +491,12 @@ sub get_os_search_list {
my @word = split(/\./, $baseos);
my @list = ();
while ($word[-1] =~ /^[0-9]+$/) {
while (@word && $word[-1] =~ /^[0-9]+$/) {
my $last = pop(@word);
if ($last =~ /^0[0-9]+$/) {
push(@list, join('.', @word, $last));
return @list;
}
while ($last >= 0) {
push(@list, join('.', @word, $last));
if ($last =~ /^0[0-9]/) {
@@ -515,17 +519,42 @@ sub get_os_search_list {
sub _profile_file_matches {
my ($filename, $osver, $shortosver, $genos, $arch) = @_;
# osver and arch specific, for example compute.sle15.x86_64.pkglist
if ($filename =~ /[^\.]*\.([^\.]*)\.([^\.]*)\./) {
return (($1 eq $osver || $1 eq $shortosver || $1 eq $genos) && $2 eq $arch);
my $stem = $filename;
foreach my $extension (qw(otherpkgs.pkglist imgcapture.exlist pkglist tmpl exlist postinstall synclist repolist)) {
if ($stem =~ s/\.\Q$extension\E$//) {
last;
}
}
$stem =~ s/\.[^.]+$// if $stem eq $filename;
my @parts = split(/\./, $stem);
# Not OS or architecture specific, for example compute.pkglist.
if (scalar(@parts) <= 1) {
return 1;
}
# osver or arch specific, for example compute.sle15.pkglist
if ($filename =~ /[^\.]*\.([^\.]*)\./) {
return ($1 eq $osver || $1 eq $shortosver || $1 eq $genos || $1 eq $arch);
shift(@parts); # profile
my $suffix = join('.', @parts);
if ($suffix eq $arch) {
return 1;
}
return 1;
my %valid_os_suffix = map { $_ => 1 } xCAT::SvrUtils::get_os_search_list($osver);
$valid_os_suffix{$genos} = 1 if $genos;
if ($valid_os_suffix{$suffix}) {
return 1;
}
# OS and architecture specific, for example compute.ubuntu24.04.x86_64.pkglist.
if (scalar(@parts) > 1 && $parts[-1] eq $arch) {
pop(@parts);
return $valid_os_suffix{join('.', @parts)} ? 1 : 0;
}
return 0;
}
sub get_file_name {
+21 -18
View File
@@ -36,6 +36,25 @@ my $httpport = "80";
my $useflowcontrol = "0";
sub _oracle_linux_distname
{
my $desc = shift;
return unless defined($desc);
my $version;
if ($desc =~ /Oracle Linux\s+((?:\d+\.)*\d+)/) {
$version = $1;
} elsif ($desc =~ /OL-((?:\d+\.)*\d+)/) {
$version = $1;
} else {
return;
}
$version =~ s/^(\d+\.\d+)\.0$/$1/;
return "ol$version";
}
sub handled_commands
{
@@ -2123,25 +2142,9 @@ sub copycd
}
close($dinfo);
}
elsif ($desc =~ /Oracle Linux/)
elsif (my $ol_distname = _oracle_linux_distname($desc))
{
#
# Attempt to auto-detect for OL8 OS, the last element
# (accessed with [-1] array index) has typically been the version
# ex: "Oracle Linux 8.3.0"
#
my @ol_version = split / /, $desc;
$distname = "ol" . $ol_version[-1];
}
elsif ($desc =~ /OL-/)
{
#
# Attempt to auto-detect for OL7 OS, the first element
# (after "-") has typically been the version
# ex: OL-7.9 Server.x86_64
#
my @ol_version = split /[- ]/, $desc;
$distname = "ol" . $ol_version[1];
$distname = $ol_distname;
}
elsif ($desc =~ /Fedora/)
{
@@ -9,6 +9,7 @@ use warnings "all";
use File::Basename;
use File::Path;
use Cwd qw(realpath);
use xCAT::SvrUtils;
sub varsubinline{
my $line=shift;
@@ -28,6 +29,19 @@ sub varsubinline{
return $line;
}
sub _profile_lookup_osbase_list {
my $osver = shift;
# OS version on s390x can contain 'sp', e.g. sles11sp1
# If OS version contains 'sp', get the index of 'sp' instead of '.'
if ($osver =~ /sles/ && $osver =~ /sp/) {
my $dotpos = rindex($osver, "sp");
return (substr($osver, 0, $dotpos));
}
return grep { $_ ne $osver } xCAT::SvrUtils::get_os_search_list($osver);
}
sub get_profile_def_filename {
my $osver = shift;
my $profile = shift;
@@ -39,34 +53,32 @@ sub get_profile_def_filename {
my $ext = shift;
my $dotpos;
# OS version on s390x can contain 'sp', e.g. sles11sp1
# If OS version contains 'sp', get the index of 'sp' instead of '.'
if ($osver =~ /sles/ && $osver =~ /sp/) {
$dotpos = rindex($osver, "sp");
} else {
$dotpos = rindex($osver, ".");
}
my $osbase = substr($osver, 0, $dotpos);
my @osbase = _profile_lookup_osbase_list($osver);
my $fallbackos;
if ($osver =~ /^leap15/) {
$fallbackos = "sle15";
}
if (-r "$base/$profile.$osver.$arch.$ext") {
return "$base/$profile.$osver.$arch.$ext";
} elsif (-r "$base/$profile.$osbase.$arch.$ext") {
return "$base/$profile.$osbase.$arch.$ext";
} elsif ($fallbackos && -r "$base/$profile.$fallbackos.$arch.$ext") {
}
foreach my $osbase (@osbase) {
if (-r "$base/$profile.$osbase.$arch.$ext") {
return "$base/$profile.$osbase.$arch.$ext";
}
}
if ($fallbackos && -r "$base/$profile.$fallbackos.$arch.$ext") {
return "$base/$profile.$fallbackos.$arch.$ext";
} elsif (-r "$base/$profile.$arch.$ext") {
return "$base/$profile.$arch.$ext";
} elsif (-r "$base/$profile.$osver.$ext") {
return "$base/$profile.$osver.$ext";
} elsif (-r "$base/$profile.$osbase.$ext") {
return "$base/$profile.$osbase.$ext";
} elsif ($fallbackos && -r "$base/$profile.$fallbackos.$ext") {
}
foreach my $osbase (@osbase) {
if (-r "$base/$profile.$osbase.$ext") {
return "$base/$profile.$osbase.$ext";
}
}
if ($fallbackos && -r "$base/$profile.$fallbackos.$ext") {
return "$base/$profile.$fallbackos.$ext";
} elsif (-r "$base/$profile.$ext") {
return "$base/$profile.$ext";
+50
View File
@@ -0,0 +1,50 @@
use strict;
use warnings;
use File::Spec;
use FindBin;
use Test::More;
my $repo_root = File::Spec->catdir($FindBin::Bin, '..', '..');
$ENV{XCATROOT} = File::Spec->catdir($repo_root, 'xCAT-server');
use lib "$FindBin::Bin/../../perl-xCAT";
use lib "$FindBin::Bin/../../xCAT-server/lib/perl";
my $anaconda = File::Spec->catfile(
$repo_root,
'xCAT-server/lib/xcat/plugins/anaconda.pm'
);
do $anaconda or die $@ || "Unable to load $anaconda: $!";
is(
xCAT_plugin::anaconda::_oracle_linux_distname('Oracle Linux 8.4.0'),
'ol8.4',
'Oracle Linux media version with trailing update zero maps to major.minor distname'
);
is(
xCAT_plugin::anaconda::_oracle_linux_distname('Oracle Linux 9.3'),
'ol9.3',
'Oracle Linux media version without trailing update zero keeps major.minor distname'
);
is(
xCAT_plugin::anaconda::_oracle_linux_distname('Oracle Linux 9.0'),
'ol9.0',
'Oracle Linux zero minor release keeps major.minor distname'
);
is(
xCAT_plugin::anaconda::_oracle_linux_distname('OL-7.9 Server.x86_64'),
'ol7.9',
'legacy OL media description maps to major.minor distname'
);
is(
xCAT_plugin::anaconda::_oracle_linux_distname('Rocky Linux 9.6'),
undef,
'Oracle Linux distname helper ignores other distributions'
);
done_testing();
@@ -0,0 +1,216 @@
use strict;
use warnings;
use Cwd qw(realpath);
use File::Spec;
use File::Temp qw(tempdir);
use FindBin;
use Test::More;
use lib "$FindBin::Bin/../../perl-xCAT";
use lib "$FindBin::Bin/../../xCAT-server/lib/perl";
use lib "$FindBin::Bin/../../xCAT-server/share/xcat/netboot/imgutils";
use xCAT::SvrUtils;
use imgutils;
my @ubuntu_2404_search = xCAT::SvrUtils::get_os_search_list('ubuntu24.04');
is_deeply(
\@ubuntu_2404_search,
['ubuntu24.04'],
'leading-zero minor release lookup does not fall back to the major-only suffix'
);
my @ubuntu_point_search = xCAT::SvrUtils::get_os_search_list('ubuntu24.04.1');
is_deeply(
\@ubuntu_point_search,
[qw(ubuntu24.04.1 ubuntu24.04.0 ubuntu24.04)],
'point release lookup can fall back within the same leading-zero minor release'
);
my @rocky_search = xCAT::SvrUtils::get_os_search_list('rocky9.6');
is_deeply(
\@rocky_search,
[qw(rocky9.6 rocky9.5 rocky9.4 rocky9.3 rocky9.2 rocky9.1 rocky9.0 rocky9)],
'non-leading-zero minor release lookup keeps existing major-version fallback behavior'
);
my @ol_search = xCAT::SvrUtils::get_os_search_list('ol8.4.0');
is_deeply(
\@ol_search,
[qw(ol8.4.0 ol8.4 ol8.3 ol8.2 ol8.1 ol8.0 ol8)],
'trailing zero update release lookup can fall back to the major.minor release'
);
ok(
xCAT::SvrUtils::_profile_file_matches(
'compute.ubuntu24.04.x86_64.pkglist',
'ubuntu24.04',
'ubuntu24',
'subiquity',
'x86_64'
),
'profile discovery treats ubuntu24.04 as the OS suffix and x86_64 as the arch suffix'
);
ok(
xCAT::SvrUtils::_profile_file_matches(
'compute.rocky9.x86_64.pkglist',
'rocky9.6',
'rocky9',
'rocky9',
'x86_64'
),
'profile discovery keeps major-version fallback assets eligible for non-leading-zero minor releases'
);
ok(
xCAT::SvrUtils::_profile_file_matches(
'compute.ol8.4.x86_64.pkglist',
'ol8.4.0',
'ol8',
'ol8',
'x86_64'
),
'profile discovery lets update releases fall back to major.minor assets'
);
ok(
!xCAT::SvrUtils::_profile_file_matches(
'compute.ubuntu24.x86_64.pkglist',
'ubuntu24.04',
'ubuntu24',
'subiquity',
'x86_64'
),
'profile discovery does not treat ubuntu24 as equivalent to ubuntu24.04'
);
ok(
xCAT::SvrUtils::_profile_file_matches(
'compute.ubuntu24.04.pkglist',
'ubuntu24.04',
'ubuntu24',
'subiquity',
'x86_64'
),
'profile discovery accepts dotted Ubuntu OS-only suffixes'
);
ok(
xCAT::SvrUtils::_profile_file_matches(
'compute.ubuntu24.04.x86_64.otherpkgs.pkglist',
'ubuntu24.04',
'ubuntu24',
'subiquity',
'x86_64'
),
'profile discovery handles compound package-list extensions after dotted Ubuntu suffixes'
);
ok(
xCAT::SvrUtils::_profile_file_matches(
'compute.otherpkgs.pkglist',
'ubuntu24.04',
'ubuntu24',
'subiquity',
'x86_64'
),
'profile discovery keeps profile-only compound package-list assets eligible'
);
my $svrutils_dir = tempdir(CLEANUP => 1);
_write_file(File::Spec->catfile($svrutils_dir, 'compute.pkglist'), "default\n");
_write_file(File::Spec->catfile($svrutils_dir, 'compute.ubuntu24.x86_64.pkglist'), "wrong\n");
is(
xCAT::SvrUtils::get_pkglist_file_name($svrutils_dir, 'compute', 'ubuntu24.04', 'x86_64', 'subiquity'),
File::Spec->catfile($svrutils_dir, 'compute.pkglist'),
'SvrUtils lookup does not fall back from ubuntu24.04 to ubuntu24'
);
_write_file(File::Spec->catfile($svrutils_dir, 'compute.ubuntu24.04.x86_64.pkglist'), "exact\n");
is(
xCAT::SvrUtils::get_pkglist_file_name($svrutils_dir, 'compute', 'ubuntu24.04', 'x86_64', 'subiquity'),
File::Spec->catfile($svrutils_dir, 'compute.ubuntu24.04.x86_64.pkglist'),
'SvrUtils lookup selects exact dotted Ubuntu arch-specific pkglist'
);
unlink File::Spec->catfile($svrutils_dir, 'compute.ubuntu24.04.x86_64.pkglist');
_write_file(File::Spec->catfile($svrutils_dir, 'compute.ubuntu24.04.pkglist'), "release\n");
is(
xCAT::SvrUtils::get_pkglist_file_name($svrutils_dir, 'compute', 'ubuntu24.04.1', 'x86_64', 'subiquity'),
File::Spec->catfile($svrutils_dir, 'compute.ubuntu24.04.pkglist'),
'SvrUtils lookup allows Ubuntu point releases to fall back to the same major.minor release'
);
my $svrutils_rpm_dir = tempdir(CLEANUP => 1);
_write_file(File::Spec->catfile($svrutils_rpm_dir, 'compute.pkglist'), "default\n");
_write_file(File::Spec->catfile($svrutils_rpm_dir, 'compute.rocky9.x86_64.pkglist'), "major\n");
is(
xCAT::SvrUtils::get_pkglist_file_name($svrutils_rpm_dir, 'compute', 'rocky9.6', 'x86_64', 'rocky9'),
File::Spec->catfile($svrutils_rpm_dir, 'compute.rocky9.x86_64.pkglist'),
'SvrUtils lookup keeps major-version fallback for non-leading-zero minor releases'
);
_write_file(File::Spec->catfile($svrutils_rpm_dir, 'compute.ol8.4.x86_64.pkglist'), "minor\n");
is(
xCAT::SvrUtils::get_pkglist_file_name($svrutils_rpm_dir, 'compute', 'ol8.4.0', 'x86_64', 'ol8'),
File::Spec->catfile($svrutils_rpm_dir, 'compute.ol8.4.x86_64.pkglist'),
'SvrUtils lookup lets update releases fall back to major.minor assets before major-only assets'
);
my $imgutils_dir = tempdir(CLEANUP => 1);
my $real_imgutils_dir = realpath($imgutils_dir) || $imgutils_dir;
_write_file(File::Spec->catfile($imgutils_dir, 'compute.pkglist'), "default\n");
_write_file(File::Spec->catfile($imgutils_dir, 'compute.ubuntu24.x86_64.pkglist'), "wrong\n");
is(
imgutils::get_profile_def_filename('ubuntu24.04', 'compute', 'x86_64', $imgutils_dir, 'pkglist'),
File::Spec->catfile($real_imgutils_dir, 'compute.pkglist'),
'imgutils lookup does not fall back from ubuntu24.04 to ubuntu24'
);
_write_file(File::Spec->catfile($imgutils_dir, 'compute.ubuntu24.04.x86_64.pkglist'), "exact\n");
is(
imgutils::get_profile_def_filename('ubuntu24.04', 'compute', 'x86_64', $imgutils_dir, 'pkglist'),
File::Spec->catfile($real_imgutils_dir, 'compute.ubuntu24.04.x86_64.pkglist'),
'imgutils lookup selects exact dotted Ubuntu arch-specific pkglist'
);
is(
imgutils::get_profile_def_filename('ubuntu24.04.1', 'compute', 'x86_64', $imgutils_dir, 'pkglist'),
File::Spec->catfile($real_imgutils_dir, 'compute.ubuntu24.04.x86_64.pkglist'),
'imgutils lookup allows Ubuntu point releases to fall back to the same major.minor release'
);
my $imgutils_rpm_dir = tempdir(CLEANUP => 1);
my $real_imgutils_rpm_dir = realpath($imgutils_rpm_dir) || $imgutils_rpm_dir;
_write_file(File::Spec->catfile($imgutils_rpm_dir, 'compute.pkglist'), "default\n");
_write_file(File::Spec->catfile($imgutils_rpm_dir, 'compute.rocky9.x86_64.pkglist'), "major\n");
is(
imgutils::get_profile_def_filename('rocky9.6', 'compute', 'x86_64', $imgutils_rpm_dir, 'pkglist'),
File::Spec->catfile($real_imgutils_rpm_dir, 'compute.rocky9.x86_64.pkglist'),
'imgutils lookup keeps major-version fallback for non-leading-zero minor releases'
);
_write_file(File::Spec->catfile($imgutils_rpm_dir, 'compute.ol8.4.x86_64.pkglist'), "minor\n");
is(
imgutils::get_profile_def_filename('ol8.4.0', 'compute', 'x86_64', $imgutils_rpm_dir, 'pkglist'),
File::Spec->catfile($real_imgutils_rpm_dir, 'compute.ol8.4.x86_64.pkglist'),
'imgutils lookup lets update releases fall back to major.minor assets before major-only assets'
);
done_testing();
sub _write_file {
my ($path, $content) = @_;
open(my $fh, '>', $path) or die "Cannot write $path: $!";
print {$fh} $content;
close($fh);
return;
}