diff --git a/Cargo.toml b/Cargo.toml index 8e3ad893..4fa5e47e 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -58,7 +58,7 @@ bottlerocket-template-helper = { path = "./bottlerocket-template-helper", versio # Settings Models bottlerocket-model-derive = { path = "./bottlerocket-settings-models/model-derive", version = "0.1" } -bottlerocket-modeled-types = { path = "./bottlerocket-settings-models/modeled-types", version = "0.12" } +bottlerocket-modeled-types = { path = "./bottlerocket-settings-models/modeled-types", version = "0.13" } bottlerocket-scalar = { path = "./bottlerocket-settings-models/scalar", version = "0.1" } bottlerocket-scalar-derive = { path = "./bottlerocket-settings-models/scalar-derive", version = "0.1" } bottlerocket-string-impls-for = { path = "./bottlerocket-settings-models/string-impls-for", version = "0.1" } @@ -76,7 +76,7 @@ settings-extension-dns = { path = "./bottlerocket-settings-models/settings-exten settings-extension-ecs = { path = "./bottlerocket-settings-models/settings-extensions/ecs", version = "0.1" } settings-extension-host-containers = { path = "./bottlerocket-settings-models/settings-extensions/host-containers", version = "0.2" } settings-extension-kernel = { path = "./bottlerocket-settings-models/settings-extensions/kernel", version = "0.1" } -settings-extension-kubernetes = { path = "./bottlerocket-settings-models/settings-extensions/kubernetes", version = "0.5" } +settings-extension-kubernetes = { path = "./bottlerocket-settings-models/settings-extensions/kubernetes", version = "0.6" } settings-extension-kubelet-device-plugins = { path = "./bottlerocket-settings-models/settings-extensions/kubelet-device-plugins", version = "0.3" } settings-extension-metrics = { path = "./bottlerocket-settings-models/settings-extensions/metrics", version = "0.1" } settings-extension-motd = { path = "./bottlerocket-settings-models/settings-extensions/motd", version = "0.1" } diff --git a/bottlerocket-settings-models/CHANGELOG.md b/bottlerocket-settings-models/CHANGELOG.md index ed257c9f..14ab38e7 100644 --- a/bottlerocket-settings-models/CHANGELOG.md +++ b/bottlerocket-settings-models/CHANGELOG.md @@ -9,7 +9,22 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 - See [unreleased changes here] -[unreleased changes here]: https://github.com/bottlerocket-os/bottlerocket-settings-sdk/compare/bottlerocket-settings-models-v0.16.0...HEAD +[unreleased changes here]: https://github.com/bottlerocket-os/bottlerocket-settings-sdk/compare/bottlerocket-settings-models-v0.17.0...HEAD + +## [0.17.0] - 2025-11-05 + +## Model Changes + +### Added + +- Added `image-minimum-gc-age` and `image-maximum-gc-age` kubernetes settings ([#87]) - Thanks @parnniti! +- Added `ids-per-pod` and `max-parallel-image-pulls` kubernetes settings ([#104]) +- Added beta options for `cpu-manager-policy-options` kubernetes settings ([#104]) + +[#87]:https://github.com/bottlerocket-os/bottlerocket-settings-sdk/pull/87 +[#104]:https://github.com/bottlerocket-os/bottlerocket-settings-sdk/pull/104 + +[0.17.0]: https://github.com/bottlerocket-os/bottlerocket-settings-sdk/compare/bottlerocket-settings-models-v0.16.0...bottlerocket-settings-models-v0.17.0 ## [0.16.0] - 2025-09-19 diff --git a/bottlerocket-settings-models/modeled-types/Cargo.toml b/bottlerocket-settings-models/modeled-types/Cargo.toml index c9da5173..fdc02a62 100644 --- a/bottlerocket-settings-models/modeled-types/Cargo.toml +++ b/bottlerocket-settings-models/modeled-types/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "bottlerocket-modeled-types" -version = "0.12.0" +version = "0.13.0" authors = [] license = "Apache-2.0 OR MIT" edition = "2021" diff --git a/bottlerocket-settings-models/modeled-types/src/kubernetes.rs b/bottlerocket-settings-models/modeled-types/src/kubernetes.rs index b347fefa..2cc53712 100644 --- a/bottlerocket-settings-models/modeled-types/src/kubernetes.rs +++ b/bottlerocket-settings-models/modeled-types/src/kubernetes.rs @@ -1337,6 +1337,12 @@ pub struct CredentialProvider { pub enum KubernetesCPUManagerPolicyOption { #[serde(rename = "full-pcpus-only")] FullPCPUsOnly, + #[serde(rename = "distribute-cpus-across-numa")] + DistributeCPUsAcrossNUMA, + #[serde(rename = "prefer-align-cpus-by-uncorecache")] + PreferAlignCPUsByUncorecache, + #[serde(rename = "strict-cpu-reservation")] + StrictCPUReservation, } #[cfg(test)] @@ -1346,8 +1352,12 @@ mod test_kubernetes_cpu_manager_policy_option { #[test] fn good_cpu_manager_policy_option() { - { - let ok = &"full-pcpus-only"; + for ok in &[ + "full-pcpus-only", + "distribute-cpus-across-numa", + "prefer-align-cpus-by-uncorecache", + "strict-cpu-reservation", + ] { KubernetesCPUManagerPolicyOption::try_from(*ok).unwrap(); } } @@ -1492,6 +1502,55 @@ mod test_kubernetes_memory_swap_behavior { // =^..^= =^..^= =^..^= =^..^= =^..^= =^..^= =^..^= =^..^= =^..^= +/// KubernetesIdsPerPodValue represents an integer that contains a valid Kubernetes idsPerPod value. +/// Must be a multiple of 65536 and less than 1<<32. Upstream validation: +/// https://github.com/kubernetes/kubernetes/blob/master/pkg/kubelet/apis/config/validation/validation_linux.go +#[derive(Debug, Clone, Eq, PartialEq, Hash, Serialize, Deserialize)] +#[serde(try_from = "i64", into = "i64")] +pub struct KubernetesIdsPerPodValue { + inner: i64, +} + +impl TryFrom for KubernetesIdsPerPodValue { + type Error = error::Error; + + fn try_from(input: i64) -> Result { + ensure!( + input % 65536 == 0 && input < (1i64 << 32), + error::InvalidKubernetesIdsPerPodValueSnafu { input } + ); + Ok(KubernetesIdsPerPodValue { inner: input }) + } +} + +impl From for i64 { + fn from(val: KubernetesIdsPerPodValue) -> Self { + val.inner + } +} + +#[cfg(test)] +mod test_kubernetes_ids_per_pod_value { + use super::KubernetesIdsPerPodValue; + use std::convert::TryFrom; + + #[test] + fn good_values() { + for ok in &[0, 65536, 131072, 196608, 4294901760] { + KubernetesIdsPerPodValue::try_from(*ok).unwrap(); + } + } + + #[test] + fn bad_values() { + for err in &[1, 65535, 65537, 4294967296] { + KubernetesIdsPerPodValue::try_from(*err).unwrap_err(); + } + } +} + +// =^..^= =^..^= =^..^= =^..^= =^..^= =^..^= =^..^= =^..^= =^..^= + /// NvidiaDevicePluginSettings contains the device sharing and partitioning related settings for Nvidia gpu. #[model(impl_default = true)] pub struct NvidiaDevicePluginSettings { diff --git a/bottlerocket-settings-models/modeled-types/src/lib.rs b/bottlerocket-settings-models/modeled-types/src/lib.rs index 7c822a4a..b4aab40d 100644 --- a/bottlerocket-settings-models/modeled-types/src/lib.rs +++ b/bottlerocket-settings-models/modeled-types/src/lib.rs @@ -159,6 +159,9 @@ pub mod error { #[snafu(display("Invalid memory swap behavior value '{}'", input))] InvalidMemorySwapBehavior { input: String }, + + #[snafu(display("Invalid Kubernetes IDs per pod value '{}'", input))] + InvalidKubernetesIdsPerPodValue { input: i64 }, } /// Creates a `ValidationError` with a consistent message for strings with regex validations diff --git a/bottlerocket-settings-models/settings-extensions/kubernetes/Cargo.toml b/bottlerocket-settings-models/settings-extensions/kubernetes/Cargo.toml index dcca0d27..7f684394 100644 --- a/bottlerocket-settings-models/settings-extensions/kubernetes/Cargo.toml +++ b/bottlerocket-settings-models/settings-extensions/kubernetes/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "settings-extension-kubernetes" -version = "0.5.0" +version = "0.6.0" authors = ["Sean P. Kelly "] license = "Apache-2.0 OR MIT" edition = "2021" diff --git a/bottlerocket-settings-models/settings-extensions/kubernetes/src/lib.rs b/bottlerocket-settings-models/settings-extensions/kubernetes/src/lib.rs index 35474f4a..befe158e 100644 --- a/bottlerocket-settings-models/settings-extensions/kubernetes/src/lib.rs +++ b/bottlerocket-settings-models/settings-extensions/kubernetes/src/lib.rs @@ -5,11 +5,11 @@ use bottlerocket_modeled_types::{ KubernetesAuthenticationMode, KubernetesBootstrapToken, KubernetesCPUManagerPolicyOption, KubernetesCloudProvider, KubernetesClusterDnsIp, KubernetesClusterName, KubernetesDurationValue, KubernetesEvictionKey, KubernetesHostnameOverrideSource, - KubernetesLabelKey, KubernetesLabelValue, KubernetesMemoryManagerPolicy, - KubernetesMemoryReservation, KubernetesMemorySwapBehavior, KubernetesQuantityValue, - KubernetesReservedResourceKey, KubernetesTaintValue, KubernetesThresholdValue, - NonNegativeInteger, SingleLineString, TopologyManagerPolicy, TopologyManagerScope, Url, - ValidBase64, ValidLinuxHostname, + KubernetesIdsPerPodValue, KubernetesLabelKey, KubernetesLabelValue, + KubernetesMemoryManagerPolicy, KubernetesMemoryReservation, KubernetesMemorySwapBehavior, + KubernetesQuantityValue, KubernetesReservedResourceKey, KubernetesTaintValue, + KubernetesThresholdValue, NonNegativeInteger, SingleLineString, TopologyManagerPolicy, + TopologyManagerScope, Url, ValidBase64, ValidLinuxHostname, }; use bottlerocket_settings_sdk::{GenerateResult, SettingsModel}; @@ -96,6 +96,8 @@ pub struct KubernetesSettingsV1 { node_ip: IpAddr, pod_infra_container_image: SingleLineString, hostname_override: ValidLinuxHostname, + ids_per_pod: KubernetesIdsPerPodValue, + max_parallel_image_pulls: i32, } type Result = std::result::Result; @@ -199,6 +201,8 @@ mod test { device_ownership_from_security_context: None, single_process_oom_kill: None, static_pods_enabled: None, + ids_per_pod: None, + max_parallel_image_pulls: None, }) ); } diff --git a/bottlerocket-settings-models/settings-models/Cargo.toml b/bottlerocket-settings-models/settings-models/Cargo.toml index f868db55..d3dcf91b 100644 --- a/bottlerocket-settings-models/settings-models/Cargo.toml +++ b/bottlerocket-settings-models/settings-models/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "bottlerocket-settings-models" -version = "0.16.0" +version = "0.17.0" authors = ["Tom Kirchner "] license = "Apache-2.0 OR MIT" edition = "2021"