Compare commits

...

4 Commits

Author SHA1 Message Date
ac90b35142 add dls::Config 2025-12-12 16:58:40 +01:00
298366a0aa Config: query files 2025-12-03 12:54:45 +01:00
ecbbb82c7a more default in dls HostConfig 2025-12-03 09:47:57 +01:00
ebd2f21d42 adjust initrd_files 2025-11-20 11:58:38 +01:00
2 changed files with 45 additions and 7 deletions

View File

@ -159,6 +159,30 @@ impl<'t> Host<'t> {
} }
} }
#[derive(Default, serde::Deserialize, serde::Serialize)]
#[serde(rename_all = "PascalCase")]
pub struct Config {
#[serde(default, deserialize_with = "deserialize_null_as_default")]
pub clusters: Vec<ClusterConfig>,
#[serde(default, deserialize_with = "deserialize_null_as_default")]
pub hosts: Vec<HostConfig>,
#[serde(default, deserialize_with = "deserialize_null_as_default")]
pub host_templates: Vec<HostConfig>,
#[serde(default, rename = "SSLConfig")]
pub ssl_config: String,
}
// compensate for go's encoder pitfalls
use serde::{Deserialize, Deserializer};
fn deserialize_null_as_default<'de, D, T>(deserializer: D) -> std::result::Result<T, D::Error>
where
T: Default + Deserialize<'de>,
D: Deserializer<'de>,
{
let opt = Option::deserialize(deserializer)?;
Ok(opt.unwrap_or_default())
}
#[derive(serde::Deserialize, serde::Serialize)] #[derive(serde::Deserialize, serde::Serialize)]
#[serde(rename_all = "PascalCase")] #[serde(rename_all = "PascalCase")]
pub struct ClusterConfig { pub struct ClusterConfig {
@ -171,15 +195,15 @@ pub struct ClusterConfig {
#[serde(rename_all = "PascalCase")] #[serde(rename_all = "PascalCase")]
pub struct HostConfig { pub struct HostConfig {
pub name: String, pub name: String,
#[serde(skip_serializing_if = "Option::is_none")] #[serde(default, skip_serializing_if = "Option::is_none")]
pub cluster_name: Option<String>, pub cluster_name: Option<String>,
#[serde(rename = "IPs")] #[serde(rename = "IPs")]
pub ips: Vec<IpAddr>, pub ips: Vec<IpAddr>,
#[serde(skip_serializing_if = "Map::is_empty")] #[serde(default, skip_serializing_if = "Map::is_empty")]
pub labels: Map<String, String>, pub labels: Map<String, String>,
#[serde(skip_serializing_if = "Map::is_empty")] #[serde(default, skip_serializing_if = "Map::is_empty")]
pub annotations: Map<String, String>, pub annotations: Map<String, String>,
#[serde(rename = "IPXE", skip_serializing_if = "Option::is_none")] #[serde(rename = "IPXE", skip_serializing_if = "Option::is_none")]
@ -189,10 +213,13 @@ pub struct HostConfig {
pub kernel: String, pub kernel: String,
pub versions: Map<String, String>, pub versions: Map<String, String>,
/// initrd config template
pub bootstrap_config: String, pub bootstrap_config: String,
#[serde(skip_serializing_if = "Map::is_empty")] /// files to add to the final initrd config, with rendering
pub initrd_files: Map<String, String>, #[serde(default, skip_serializing_if = "Vec::is_empty")]
pub initrd_files: Vec<crate::File>,
/// system config template
pub config: String, pub config: String,
} }

View File

@ -52,7 +52,7 @@ pub struct User {
pub gid: Option<u32>, pub gid: Option<u32>,
} }
#[derive(Debug, serde::Deserialize, serde::Serialize)] #[derive(Debug, PartialEq, Eq, serde::Deserialize, serde::Serialize)]
pub struct File { pub struct File {
pub path: String, pub path: String,
#[serde(skip_serializing_if = "Option::is_none")] #[serde(skip_serializing_if = "Option::is_none")]
@ -61,10 +61,21 @@ pub struct File {
pub kind: FileKind, pub kind: FileKind,
} }
#[derive(Debug, serde::Deserialize, serde::Serialize)] #[derive(Debug, PartialEq, Eq, serde::Deserialize, serde::Serialize)]
#[serde(rename_all = "snake_case")] #[serde(rename_all = "snake_case")]
pub enum FileKind { pub enum FileKind {
Content(String), Content(String),
Symlink(String), Symlink(String),
Dir(bool), Dir(bool),
} }
// ------------------------------------------------------------------------
impl Config {
pub fn has_file(&self, path: &str) -> bool {
self.files.iter().any(|f| f.path == path)
}
pub fn file(&self, path: &str) -> Option<&File> {
self.files.iter().find(|f| f.path == path)
}
}