"""Unit tests for the App Runner Flask blueprint."""

from unittest.mock import MagicMock

import pytest
from flask import Flask

import products.paas.app_runner as app_runner

pytestmark = pytest.mark.unit


@pytest.fixture
def client():
    app = Flask(__name__)
    app.register_blueprint(app_runner.bp)
    app.testing = True
    return app.test_client()


# ── /env_vars ────────────────────────────────────────────────────────────────
def test_env_vars_all(client, monkeypatch):
    monkeypatch.setenv("CQA_UNIT_PROBE", "1")
    resp = client.get("/api/app_runner/env_vars")
    assert resp.status_code == 200
    body = resp.get_json()
    assert body["status"] == "success" and body["count"] >= 1


def test_env_vars_specific_found(client, monkeypatch):
    monkeypatch.setenv("CQA_UNIT_KEY", "the-value")
    resp = client.get("/api/app_runner/env_vars/CQA_UNIT_KEY")
    assert resp.status_code == 200
    assert resp.get_json()["data"]["value"] == "the-value"


def test_env_vars_specific_missing(client, monkeypatch):
    monkeypatch.delenv("CQA_MISSING_KEY", raising=False)
    resp = client.get("/api/app_runner/env_vars/CQA_MISSING_KEY")
    assert resp.status_code == 404
    assert resp.get_json()["status"] == "error"


# ── /get_access_token ────────────────────────────────────────────────────────
def test_get_access_token_missing_domain(client):
    resp = client.get("/api/app_runner/get_access_token")
    assert resp.status_code == 400


def test_get_access_token_success(client, mocker):
    zts = MagicMock()
    zts.get_access_token.return_value = MagicMock(access_token="abc123")
    mocker.patch.object(app_runner.ZTSClient, "with_cert", return_value=zts)
    resp = client.get("/api/app_runner/get_access_token?product_domain=dom")
    assert resp.status_code == 200
    assert resp.get_json()["access_token"] == "abc123"


def test_get_access_token_failure(client, mocker):
    mocker.patch.object(app_runner.ZTSClient, "with_cert", side_effect=RuntimeError("cert error"))
    resp = client.get("/api/app_runner/get_access_token?product_domain=dom")
    assert resp.status_code == 500
    assert resp.get_json()["success"] is False


# ── /send_request ────────────────────────────────────────────────────────────
def test_send_request_missing_host(client):
    resp = client.get("/api/app_runner/send_request")
    assert resp.status_code == 400


def test_send_request_success(client, mocker):
    mocker.patch.object(app_runner.requests, "get", return_value=MagicMock())
    resp = client.get("/api/app_runner/send_request?host=http://x")
    assert resp.status_code == 200
    assert resp.get_json()["success"] is True


def test_send_request_failure(client, mocker):
    mocker.patch.object(
        app_runner.requests, "get", side_effect=app_runner.requests.RequestException("down")
    )
    resp = client.get("/api/app_runner/send_request?host=http://x")
    assert resp.status_code == 500


# ── /validate_volume ─────────────────────────────────────────────────────────
def test_validate_volume_missing_params(client):
    resp = client.post("/api/app_runner/validate_volume", json={})
    assert resp.status_code == 400


def test_validate_volume_file_exists(client, tmp_path):
    f = tmp_path / "secret.txt"
    f.write_text("hello", encoding="utf-8")
    resp = client.post(
        "/api/app_runner/validate_volume", json={"key": "secret.txt", "path": str(tmp_path)}
    )
    assert resp.status_code == 200
    assert resp.get_json()["content"] == "hello"


def test_validate_volume_file_missing(client, tmp_path):
    resp = client.post(
        "/api/app_runner/validate_volume", json={"key": "nope.txt", "path": str(tmp_path)}
    )
    assert resp.status_code == 404
