pub mod fstype;
pub mod partition;
mod utils;
use std::{fs, path::PathBuf};
use anyhow::Result;
use fstype::FsType;
use partition::PartitionConfig;
use serde::Deserialize;
#[derive(Debug, Clone, Deserialize)]
pub struct RootFSConfigFile {
pub metadata: RootFSMeta,
#[serde(default)]
pub partition: PartitionConfig,
}
impl RootFSConfigFile {
pub const LBA_SIZE: usize = 512;
pub fn load(path: &PathBuf) -> Result<Self> {
let content = fs::read_to_string(path)?;
Self::load_from_str(&content)
}
pub fn load_from_str(content: &str) -> Result<Self> {
let config: RootFSConfigFile = toml::from_str(content)?;
Ok(config)
}
}
#[derive(Debug, Clone, Copy, Deserialize)]
pub struct RootFSMeta {
pub fs_type: FsType,
#[serde(deserialize_with = "utils::size::deserialize_size")]
pub size: usize,
}
#[cfg(test)]
mod tests {
use std::io::Write;
use super::*;
use tempfile::NamedTempFile;
#[test]
fn test_load_from_valid_file() {
let config_content = r#"
[metadata]
fs_type = "fat32"
size = "1024M"
"#;
let mut temp_file = NamedTempFile::new().expect("Failed to create temp file");
temp_file
.write_all(config_content.as_bytes())
.expect("Failed to write to temp file");
let config_path = PathBuf::from(temp_file.path());
let config = RootFSConfigFile::load(&config_path).expect("Failed to load config");
assert_eq!(config.metadata.fs_type, FsType::Fat32);
assert_eq!(config.metadata.size, 1024 * 1024 * 1024); }
#[test]
fn test_load_from_valid_str() {
let config_content = r#"
[metadata]
fs_type = "fat32"
size = "512M"
"#;
let config = RootFSConfigFile::load_from_str(config_content)
.expect("Failed to load config from str");
assert_eq!(config.metadata.fs_type, FsType::Fat32);
assert_eq!(config.metadata.size, 512 * 1024 * 1024); }
#[test]
fn test_load_from_invalid_fs_type() {
let config_content = r#"
[metadata]
fs_type = "ABCDE"
size = "512M"
"#;
assert!(RootFSConfigFile::load_from_str(config_content).is_err());
}
#[test]
fn test_load_from_valid_str_size_integer() {
let config_content = r#"
[metadata]
fs_type = "fat32"
size = 1048576
"#;
let config = RootFSConfigFile::load_from_str(config_content)
.expect("Failed to load config from str");
assert_eq!(config.metadata.fs_type, FsType::Fat32);
assert_eq!(config.metadata.size, 1048576); }
#[test]
fn test_load_from_valid_str_size_bytes_str() {
let config_content = r#"
[metadata]
fs_type = "fat32"
size = "1048576"
"#;
let config = RootFSConfigFile::load_from_str(config_content)
.expect("Failed to load config from str");
assert_eq!(config.metadata.fs_type, FsType::Fat32);
assert_eq!(config.metadata.size, 1048576); }
#[test]
fn test_load_from_invalid_file() {
let temp_file = NamedTempFile::new().expect("Failed to create temp file");
let config_path = PathBuf::from(temp_file.path());
assert!(RootFSConfigFile::load(&config_path).is_err());
}
#[test]
fn test_load_from_invalid_size_str() {
let invalid_config_content = r#"
[metadata]
fs_type = "fat32"
size = "not_a_size"
"#;
assert!(RootFSConfigFile::load_from_str(invalid_config_content).is_err());
}
#[test]
fn test_load_from_invalid_size_array() {
let invalid_config_content = r#"
[metadata]
fs_type = "fat32"
size = ["not_a_size"]
"#;
assert!(RootFSConfigFile::load_from_str(invalid_config_content).is_err());
}
}