//! Safety bindings: lint, scan_sql, is_safe, PII, semantics, glossary.

use crate::schema::Schema;
use pyo3::prelude::*;

/// Lint SQL for anti-patterns (SELECT *, missing WHERE, etc.).
#[pyfunction]
pub fn lint(py: Python<'_>, sql: &str, schema: &Schema) -> PyResult<PyObject> {
    let start = std::time::Instant::now();
    let result = altimate_core::linter::lint(sql, &schema.inner);
    crate::sdk::timed_emit("lint", start);
    crate::convert::to_py_result(py, &result)
}

/// Scan SQL for injection threats (10 detection rules).
#[pyfunction]
pub fn scan_sql(py: Python<'_>, sql: &str) -> PyResult<PyObject> {
    let start = std::time::Instant::now();
    let config = altimate_core::safety::SafetyConfig::default();
    let result = altimate_core::safety::scan_sql(sql, &config);
    crate::sdk::timed_emit("scanSql", start);
    crate::convert::to_py_result(py, &result)
}

/// Quick boolean check: is this SQL safe from injection?
#[pyfunction]
pub fn is_safe(sql: &str) -> bool {
    let start = std::time::Instant::now();
    let result = altimate_core::safety::is_safe(sql);
    crate::sdk::timed_emit("isSafe", start);
    result
}

/// Classify schema columns for PII exposure.
#[pyfunction]
pub fn classify_pii(py: Python<'_>, schema: &Schema) -> PyResult<PyObject> {
    let start = std::time::Instant::now();
    let result = altimate_core::pii::classify_schema(&schema.inner);
    crate::sdk::timed_emit("classifyPii", start);
    crate::convert::to_py_result(py, &result)
}

/// Check if a query accesses PII columns.
#[pyfunction]
pub fn check_query_pii(py: Python<'_>, sql: &str, schema: &Schema) -> PyResult<PyObject> {
    let start = std::time::Instant::now();
    let result = altimate_core::pii::check_query_pii(sql, &schema.inner);
    crate::sdk::timed_emit("checkQueryPii", start);
    crate::convert::to_py_result(py, &result)
}

/// Run semantic validation rules (cartesian products, wrong JOINs, NULL misuse).
#[pyfunction]
pub fn check_semantics(py: Python<'_>, sql: &str, schema: &Schema) -> PyResult<PyObject> {
    let start = std::time::Instant::now();
    let result = crate::runtime::runtime().block_on(
        altimate_core::semantic::engine::check_semantics(sql, &schema.inner),
    );
    crate::sdk::timed_emit("checkSemantics", start);
    crate::convert::to_py_result(py, &result)
}

/// Resolve a business term to schema elements via fuzzy matching.
#[pyfunction]
pub fn resolve_term(py: Python<'_>, term: &str, schema: &Schema) -> PyResult<PyObject> {
    let start = std::time::Instant::now();
    let result = altimate_core::glossary::resolve_term(term, &schema.inner);
    crate::sdk::timed_emit("resolveTerm", start);
    crate::convert::to_py_result(py, &result)
}
