athena_rs 3.23.0

Hyper performant polyglot Database driver
Documentation
//! Unexpected-column delta policy for `/debug/schema`.
//!
//! This module owns collecting observed columns that are not part of expected
//! schema requirements while preserving deterministic observed-column order.

use std::collections::BTreeSet;

/// Collects observed columns that are unexpected by expected schema rules.
pub(super) fn collect_unexpected_columns(
    observed_columns: &[String],
    expected_set: &BTreeSet<String>,
) -> Vec<String> {
    observed_columns
        .iter()
        .filter(|column| !expected_set.contains((*column).as_str()))
        .cloned()
        .collect()
}

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

    #[test]
    /// Preserves observed-column order when reporting unexpected columns.
    fn collect_unexpected_columns_preserves_observed_order() {
        let observed = vec![
            "request_id".to_string(),
            "extra_col".to_string(),
            "status_code".to_string(),
        ];
        let expected_set: BTreeSet<String> = ["request_id".to_string(), "status_code".to_string()]
            .into_iter()
            .collect();

        let unexpected = collect_unexpected_columns(&observed, &expected_set);

        assert_eq!(unexpected, vec!["extra_col".to_string()]);
    }

    #[test]
    /// Treats duplicate observed values as expected when expected set contains key.
    fn collect_unexpected_columns_treats_duplicate_observed_values_as_expected() {
        let observed = vec![
            "request_id".to_string(),
            "request_id".to_string(),
            "status_code".to_string(),
        ];
        let expected_set: BTreeSet<String> = ["request_id".to_string(), "status_code".to_string()]
            .into_iter()
            .collect();

        let unexpected = collect_unexpected_columns(&observed, &expected_set);

        assert!(unexpected.is_empty());
    }
}