//! Integration smoke test for `cellos-broker-env`.
//!
//! Scope: smoke wires only — verifies the public `EnvSecretBroker` API surface
//! constructs, resolves a present env-injected secret, and surfaces an error for
//! a missing key. Comprehensive cases live in the inline `#[cfg(test)]` block.

use cellos_broker_env::EnvSecretBroker;
use cellos_core::ports::{RuntimeSecretLeaseRequest, SecretBroker};

/// Use a per-test env var name to avoid collisions with the inline tests
/// running in the same process.
const SMOKE_KEY: &str = "SMOKE_INTEGRATION_TOKEN";
const SMOKE_ENV_VAR: &str = "CELLOS_SECRET_SMOKE_INTEGRATION_TOKEN";

#[tokio::test]
async fn smoke_construct_and_resolve_present_key() {
    std::env::set_var(SMOKE_ENV_VAR, "smoke-value");
    let broker = EnvSecretBroker::new();
    let view = broker
        .resolve(SMOKE_KEY, "smoke-cell", 60)
        .await
        .expect("smoke: resolve present key must succeed");
    assert_eq!(view.key, SMOKE_KEY);
    assert_eq!(view.value.as_str(), "smoke-value");
    std::env::remove_var(SMOKE_ENV_VAR);
}

#[tokio::test]
async fn smoke_resolve_missing_key_errors() {
    std::env::remove_var("CELLOS_SECRET_SMOKE_DEFINITELY_NOT_SET_XYZ");
    let broker = EnvSecretBroker::new();
    let err = broker
        .resolve("SMOKE_DEFINITELY_NOT_SET_XYZ", "smoke-cell", 60)
        .await
        .expect_err("smoke: missing key must error");
    let msg = err.to_string();
    assert!(
        msg.contains("CELLOS_SECRET_SMOKE_DEFINITELY_NOT_SET_XYZ"),
        "expected error to mention the env var name, got: {msg}"
    );
}

#[tokio::test]
async fn smoke_revoke_for_cell_is_noop() {
    let broker = EnvSecretBroker::new();
    // Documented no-op for env-injected secrets.
    broker
        .revoke_for_cell("smoke-cell")
        .await
        .expect("smoke: revoke_for_cell must succeed");
}

/// TEST-01 (J-H3) — the env broker has no upstream lease to prepare, so the
/// `RuntimeLeasedBroker` delivery mode must surface the typed default error
/// rather than silently succeeding. Operators that misconfigure the broker
/// for that delivery mode then see a clear, greppable message at admit-time.
#[tokio::test]
async fn smoke_prepare_runtime_secret_lease_is_unsupported() {
    let broker = EnvSecretBroker::new();
    let requests = [RuntimeSecretLeaseRequest {
        key: "SMOKE_LEASE_KEY".into(),
        ttl_seconds: 60,
    }];
    let err = broker
        .prepare_runtime_secret_lease("smoke-cell", &requests)
        .await
        .expect_err("smoke: env broker must reject runtimeLeasedBroker");
    let msg = err.to_string().to_lowercase();
    assert!(
        msg.contains("not supported") || msg.contains("unsupported"),
        "expected unsupported-error message, got: {err}"
    );
}
