// SPDX-FileCopyrightText: 2024-2025 The n5i Project
//
// SPDX-License-Identifier: AGPL-3.0-or-later

use serde::{Deserialize, Serialize};

// A helper for skipping deserialization of values that default to false
#[inline]
pub fn is_false(v: &bool) -> bool {
    !*v
}

#[inline]
pub fn true_default() -> bool {
    true
}

/// A type that can be serialized into a string, but can also be various other types
#[derive(Serialize, Deserialize, Clone, Debug, PartialEq)]
#[serde(untagged)]
pub enum StringLike {
    String(String),
    Int(i64),
    Bool(bool),
    Float(f64),
}

impl From<StringLike> for String {
    fn from(s: StringLike) -> Self {
        match s {
            StringLike::String(s) => s,
            StringLike::Int(i) => i.to_string(),
            StringLike::Bool(b) => b.to_string(),
            StringLike::Float(f) => f.to_string(),
        }
    }
}

#[derive(Serialize, Deserialize, Clone, Debug, PartialEq)]
#[serde(untagged)]
pub enum StringOrNumber {
    String(String),
    Int(i64),
    Float(f64),
}

#[cfg(test)]
mod tests {
    use super::*;

    #[test]
    fn test_is_false() {
        assert!(is_false(&false));
        assert!(!is_false(&true));
    }

    #[test]
    fn test_stringlike() {
        assert_eq!(
            Into::<String>::into(StringLike::String("Hello world".to_string())),
            "Hello world".to_string()
        );
        assert_eq!(
            Into::<String>::into(StringLike::Int(100)),
            "100".to_string()
        );
        assert_eq!(
            Into::<String>::into(StringLike::Bool(true)),
            "true".to_string()
        );
        assert_eq!(
            Into::<String>::into(StringLike::Float(1.23)),
            "1.23".to_string()
        );
    }
}
