diff --git a/upup/pkg/fi/nodeup/nodetasks/package.go b/upup/pkg/fi/nodeup/nodetasks/package.go index ec870afe7a67e..63c08dc92d471 100644 --- a/upup/pkg/fi/nodeup/nodetasks/package.go +++ b/upup/pkg/fi/nodeup/nodetasks/package.go @@ -22,7 +22,6 @@ import ( "os/exec" "path" "reflect" - "slices" "strings" "sync" @@ -328,10 +327,7 @@ func (_ *Package) RenderLocal(t *local.LocalTarget, a, e, changes *Package) erro env = append(env, "DEBIAN_FRONTEND=noninteractive") } else if d.IsRHELFamily() { - if slices.Contains([]distributions.Distribution{ - distributions.DistributionRhel8, distributions.DistributionRocky8, - distributions.DistributionRhel9, distributions.DistributionRocky9, - }, d) { + if d.HasDNF() { args = []string{"/usr/bin/dnf", "install", "-y", "--setopt=install_weak_deps=False"} } else { args = []string{"/usr/bin/yum", "install", "-y"} diff --git a/util/pkg/distributions/distributions.go b/util/pkg/distributions/distributions.go index 7375bc28e8eb1..3a47fb2f72987 100644 --- a/util/pkg/distributions/distributions.go +++ b/util/pkg/distributions/distributions.go @@ -19,6 +19,8 @@ package distributions import ( "fmt" "os" + + "k8s.io/klog/v2" ) // Distribution represents a particular version of an operating system. @@ -38,20 +40,27 @@ type Distribution struct { } var ( - DistributionDebian10 = Distribution{packageFormat: "deb", project: "debian", id: "buster", version: 10} - DistributionDebian11 = Distribution{packageFormat: "deb", project: "debian", id: "bullseye", version: 11} - DistributionDebian12 = Distribution{packageFormat: "deb", project: "debian", id: "bookworm", version: 12} - DistributionUbuntu2004 = Distribution{packageFormat: "deb", project: "ubuntu", id: "focal", version: 20.04} - DistributionUbuntu2204 = Distribution{packageFormat: "deb", project: "ubuntu", id: "jammy", version: 22.04} - DistributionUbuntu2404 = Distribution{packageFormat: "deb", project: "ubuntu", id: "noble", version: 24.04} - DistributionAmazonLinux2 = Distribution{packageFormat: "rpm", project: "amazonlinux2", id: "amazonlinux2", version: 0} - DistributionAmazonLinux2023 = Distribution{packageFormat: "rpm", project: "amazonlinux2023", id: "amzn", version: 2023} + // Debian-family distros + DistributionDebian10 = Distribution{packageFormat: "deb", project: "debian", id: "buster", version: 10} + DistributionDebian11 = Distribution{packageFormat: "deb", project: "debian", id: "bullseye", version: 11} + DistributionDebian12 = Distribution{packageFormat: "deb", project: "debian", id: "bookworm", version: 12} + DistributionDebian13 = Distribution{packageFormat: "deb", project: "debian", id: "trixie", version: 13} + DistributionUbuntu2004 = Distribution{packageFormat: "deb", project: "ubuntu", id: "focal", version: 20.04} + DistributionUbuntu2204 = Distribution{packageFormat: "deb", project: "ubuntu", id: "jammy", version: 22.04} + DistributionUbuntu2404 = Distribution{packageFormat: "deb", project: "ubuntu", id: "noble", version: 24.04} + + // Redhat-family distros DistributionRhel8 = Distribution{packageFormat: "rpm", project: "rhel", id: "rhel8", version: 8} DistributionRhel9 = Distribution{packageFormat: "rpm", project: "rhel", id: "rhel9", version: 9} DistributionRocky8 = Distribution{packageFormat: "rpm", project: "rocky", id: "rocky8", version: 8} DistributionRocky9 = Distribution{packageFormat: "rpm", project: "rocky", id: "rocky9", version: 9} - DistributionFlatcar = Distribution{packageFormat: "", project: "flatcar", id: "flatcar", version: 0} - DistributionContainerOS = Distribution{packageFormat: "", project: "containeros", id: "containeros", version: 0} + DistributionFedora41 = Distribution{packageFormat: "rpm", project: "fedora", id: "fedora41", version: 41} + DistributionAmazonLinux2 = Distribution{packageFormat: "rpm", project: "amazonlinux2", id: "amazonlinux2", version: 0} + DistributionAmazonLinux2023 = Distribution{packageFormat: "rpm", project: "amazonlinux2023", id: "amzn", version: 2023} + + // Immutable distros + DistributionFlatcar = Distribution{packageFormat: "", project: "flatcar", id: "flatcar", version: 0} + DistributionContainerOS = Distribution{packageFormat: "", project: "containeros", id: "containeros", version: 0} ) // IsDebianFamily returns true if this distribution uses deb packages and generally follows debian package names @@ -69,6 +78,25 @@ func (d *Distribution) IsRHELFamily() bool { return d.packageFormat == "rpm" } +// HasDNF returns true if this distribution uses dnf +func (d *Distribution) HasDNF() bool { + if !d.IsRHELFamily() { + return false + } + // All our RHEL distros support DNF at this point, it seems + switch d.project { + case "rhel": + return d.version >= 8 + case "rocky": + return d.version >= 8 + case "fedora": + return d.version >= 22 + default: + klog.Warningf("unknown project for HasDNF (%q), assuming does support dnf", d.project) + return true + } +} + // IsSystemd returns true if this distribution uses systemd func (d *Distribution) IsSystemd() bool { return true diff --git a/util/pkg/distributions/identify.go b/util/pkg/distributions/identify.go index 060074ebe8b7a..60b265c413f70 100644 --- a/util/pkg/distributions/identify.go +++ b/util/pkg/distributions/identify.go @@ -58,6 +58,8 @@ func FindDistribution(rootfs string) (Distribution, error) { return DistributionDebian11, nil case "debian-12": return DistributionDebian12, nil + case "fedora-41": + return DistributionFedora41, nil case "ubuntu-20.04": return DistributionUbuntu2004, nil case "ubuntu-22.04": @@ -88,5 +90,5 @@ func FindDistribution(rootfs string) (Distribution, error) { // Some distros are not supported klog.V(2).Infof("Contents of /etc/os-release:\n%s", osReleaseBytes) - return Distribution{}, fmt.Errorf("unsupported distro: %s", distro) + return Distribution{}, fmt.Errorf("unsupported distro %q", distro) } diff --git a/util/pkg/distributions/identify_test.go b/util/pkg/distributions/identify_test.go index f1dbaf1fe45d8..5935408184d19 100644 --- a/util/pkg/distributions/identify_test.go +++ b/util/pkg/distributions/identify_test.go @@ -41,17 +41,17 @@ func TestFindDistribution(t *testing.T) { }, { rootfs: "centos7", - err: fmt.Errorf("unsupported distro: centos-7"), + err: fmt.Errorf("unsupported distro %q", "centos-7"), expected: Distribution{}, }, { rootfs: "centos8", - err: fmt.Errorf("unsupported distro: centos-8"), + err: fmt.Errorf("unsupported distro %q", "centos-8"), expected: Distribution{}, }, { rootfs: "coreos", - err: fmt.Errorf("unsupported distro: coreos-2247.7.0"), + err: fmt.Errorf("unsupported distro %q", "coreos-2247.7.0"), expected: Distribution{}, }, { @@ -61,12 +61,12 @@ func TestFindDistribution(t *testing.T) { }, { rootfs: "debian8", - err: fmt.Errorf("unsupported distro: debian-8"), + err: fmt.Errorf("unsupported distro %q", "debian-8"), expected: Distribution{}, }, { rootfs: "debian9", - err: fmt.Errorf("unsupported distro: debian-9"), + err: fmt.Errorf("unsupported distro %q", "debian-9"), expected: Distribution{}, }, { @@ -91,7 +91,7 @@ func TestFindDistribution(t *testing.T) { }, { rootfs: "rhel7", - err: fmt.Errorf("unsupported distro: rhel-7.8"), + err: fmt.Errorf("unsupported distro %q", "rhel-7.8"), expected: Distribution{}, }, { @@ -116,7 +116,7 @@ func TestFindDistribution(t *testing.T) { }, { rootfs: "ubuntu1604", - err: fmt.Errorf("unsupported distro: ubuntu-16.04"), + err: fmt.Errorf("unsupported distro %q", "ubuntu-16.04"), expected: Distribution{}, }, {