//! Database L2 Usage Metering

use serde::{Deserialize, Serialize};

/// Database service usage metrics
#[derive(Debug, Clone, Default, Serialize, Deserialize)]
pub struct DatabaseUsage {
    /// Number of queries executed
    pub queries: u64,
    /// Number of vector searches
    pub vector_searches: u64,
    /// Storage used in bytes
    pub storage_bytes: u64,
    /// Number of documents stored
    pub documents: u64,
    /// Number of indexes maintained
    pub indexes: u32,
}

impl DatabaseUsage {
    /// Create new database usage
    pub fn new() -> Self {
        Self::default()
    }

    /// Add queries
    pub fn with_queries(mut self, count: u64) -> Self {
        self.queries = count;
        self
    }

    /// Add vector searches
    pub fn with_vector_searches(mut self, count: u64) -> Self {
        self.vector_searches = count;
        self
    }

    /// Add storage
    pub fn with_storage(mut self, bytes: u64) -> Self {
        self.storage_bytes = bytes;
        self
    }

    /// Add documents
    pub fn with_documents(mut self, count: u64) -> Self {
        self.documents = count;
        self
    }

    /// Add indexes
    pub fn with_indexes(mut self, count: u32) -> Self {
        self.indexes = count;
        self
    }

    /// Convert storage to GB
    pub fn storage_gb(&self) -> f64 {
        self.storage_bytes as f64 / 1_073_741_824.0
    }

    /// Get queries in millions
    pub fn queries_millions(&self) -> f64 {
        self.queries as f64 / 1_000_000.0
    }

    /// Get vector searches in millions
    pub fn vector_searches_millions(&self) -> f64 {
        self.vector_searches as f64 / 1_000_000.0
    }
}

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

    #[test]
    fn test_database_usage() {
        let usage = DatabaseUsage::new()
            .with_queries(5_000_000)
            .with_vector_searches(100_000)
            .with_storage(536_870_912) // 0.5 GB
            .with_documents(10_000)
            .with_indexes(5);

        assert_eq!(usage.queries_millions(), 5.0);
        assert_eq!(usage.vector_searches_millions(), 0.1);
        assert_eq!(usage.storage_gb(), 0.5);
    }
}
