use actix_web::{web, HttpResponse};

use crate::AppState;

#[derive(serde::Deserialize)]
pub struct AddRegistryRequest {
    pub url: String,
}

#[derive(serde::Deserialize)]
pub struct CheckRegistryQuery {
    pub url: String,
}

pub async fn add_url_handler(
    state: web::Data<AppState>,
    body: web::Json<AddRegistryRequest>,
) -> HttpResponse {
    let url = &body.url;

    // Add to bloom filter
    state.bloom.set(url);

    // Add to Athena DB if available
    if let Some(ref athena) = state.athena {
        if let Err(e) = crate::data::add_url_to_registry(athena, url, "manual").await {
            tracing::warn!("Failed to add URL to DB registry: {}", e);
        }
    }

    if let Some(ref redis_client) = state.redis_client {
        match redis_client.get_multiplexed_async_connection().await {
            Ok(mut conn) => {
                if let Err(e) = crate::cache::redis_registry::add_url(&mut conn, url).await {
                    tracing::warn!("Failed to add URL to Redis: {}", e);
                }
            }
            Err(e) => {
                tracing::warn!("Failed to connect to Redis: {}", e);
            }
        }
    }

    state.metrics.registry_checks_total.inc();

    HttpResponse::Ok().json(serde_json::json!({ "status": "added", "url": url }))
}

pub async fn check_url_handler(
    state: web::Data<AppState>,
    query: web::Query<CheckRegistryQuery>,
) -> HttpResponse {
    let url = &query.url;

    state.metrics.registry_checks_total.inc();

    // Check bloom filter first (fastest)
    if !state.bloom.check(url) {
        state.metrics.cache_misses_total.inc();
        return HttpResponse::Ok().json(serde_json::json!({
            "url": url,
            "found": false,
            "source": "bloom_filter"
        }));
    }

    if let Some(ref redis_client) = state.redis_client {
        match redis_client.get_multiplexed_async_connection().await {
            Ok(mut conn) => match crate::cache::redis_registry::check_url(&mut conn, url).await {
                Ok(found) => {
                    if found {
                        state.metrics.cache_hits_total.inc();
                    } else {
                        state.metrics.cache_misses_total.inc();
                    }
                    return HttpResponse::Ok().json(serde_json::json!({
                        "url": url,
                        "found": found,
                        "source": "redis"
                    }));
                }
                Err(e) => {
                    tracing::warn!("Redis registry check failed: {}", e);
                }
            },
            Err(e) => {
                tracing::warn!("Failed to connect to Redis: {}", e);
            }
        }
    }

    state.metrics.cache_misses_total.inc();
    HttpResponse::Ok().json(serde_json::json!({
        "url": url,
        "found": false,
        "source": "no_backend"
    }))
}
