Spaces:
Running
Running
Download tests/test_admin.py from BravoRobots/lexia: direct link, hf CLI and curl.
- Browser
- Download file 5.68 kB
-
https://huggingface.co/spaces/BravoRobots/lexia/resolve/main/tests/test_admin.py
- Command line
-
hf download hf://spaces/BravoRobots/lexia/tests/test_admin.py
-
curl -L -o test_admin.py https://huggingface.co/spaces/BravoRobots/lexia/resolve/main/tests/test_admin.py
5.68 kB
| import json | |
| import pytest | |
| pytest.importorskip("fastapi") | |
| pytest.importorskip("httpx") | |
| from fastapi import FastAPI # noqa: E402 | |
| from fastapi.testclient import TestClient # noqa: E402 | |
| class VozFalsa: | |
| frecuencia_destino = 16000 | |
| def sintetizar(self, texto): | |
| import numpy as np | |
| yield np.zeros(1600, dtype=np.int16) | |
| class TranscriptorFalso: | |
| def transcribe(self, muestras): | |
| return "¿tengo que avisar de que uso un chatbot?" | |
| class OrquestadorFalso: | |
| def ask(self, pregunta): | |
| from types import SimpleNamespace | |
| respuesta = SimpleNamespace(text="Sí, debe informarlo.", citations=[]) | |
| return SimpleNamespace(answer=respuesta, topic="TRANSPARENCIA") | |
| def entorno(tmp_path, monkeypatch): | |
| monkeypatch.setenv("LEXIA_RUNTIME", str(tmp_path / "rt")) | |
| import importlib | |
| from pathlib import Path | |
| from lexia.core import paths as modulo_paths | |
| importlib.reload(modulo_paths) | |
| for nombre in ("lexia.core.config", "lexia.core.logging", "lexia.admin.security"): | |
| importlib.reload(importlib.import_module(nombre)) | |
| from lexia.admin import routes as modulo_rutas | |
| from lexia.admin import security | |
| from lexia.web import remote_voice | |
| from lexia.web.camera import CameraStream | |
| importlib.reload(modulo_rutas) | |
| modulo_paths.ensure_runtime() | |
| camara = CameraStream() | |
| sesion = remote_voice.RemoteVoiceSession() | |
| consola = remote_voice.RemoteVoiceConsole( | |
| OrquestadorFalso(), TranscriptorFalso(), VozFalsa(), sesion | |
| ) | |
| app = FastAPI() | |
| panel = Path(modulo_rutas.__file__).resolve().parent.parent / "static" / "admin.html" | |
| modulo_rutas.register_admin( | |
| app, panel=panel, camera=camara, session=sesion, console_provider=lambda: consola | |
| ) | |
| return TestClient(app), security.ensure_token(), camara, sesion | |
| def test_sin_token_no_se_ve_nada(entorno): | |
| cliente, *_ = entorno | |
| for ruta in ("/api/admin/overview", "/api/admin/logs", "/api/admin/camera/stream"): | |
| assert cliente.get(ruta).status_code == 401, ruta | |
| def test_un_token_incorrecto_no_entra(entorno): | |
| cliente, *_ = entorno | |
| assert cliente.post("/api/admin/login", json={"token": "0" * 40}).status_code == 401 | |
| def test_con_token_se_entra_y_se_ve_el_estado(entorno): | |
| cliente, token, *_ = entorno | |
| assert cliente.post("/api/admin/login", json={"token": token}).status_code == 200 | |
| datos = cliente.get("/api/admin/overview").json() | |
| assert "…" in datos["token"], "el token nunca se muestra entero" | |
| assert datos["camera"]["enabled"] is False, "la cámara arranca apagada" | |
| assert datos["camera"]["recording"] is False | |
| assert "admin" not in datos["settings"], "los ajustes públicos no llevan el token" | |
| def test_la_camara_apagada_no_emite(entorno): | |
| cliente, token, camara, _ = entorno | |
| cliente.post("/api/admin/login", json={"token": token}) | |
| assert cliente.get("/api/admin/camera/stream").status_code == 409 | |
| cliente.post("/api/admin/camera", json={"enabled": True}) | |
| assert camara.enabled is True | |
| cliente.post("/api/admin/camera", json={"enabled": False}) | |
| assert camara.enabled is False | |
| def test_el_token_no_se_puede_escribir_desde_los_ajustes(entorno): | |
| cliente, token, *_ = entorno | |
| cliente.post("/api/admin/login", json={"token": token}) | |
| respuesta = cliente.patch("/api/admin/settings", json={"admin": {"token": "x" * 40}}) | |
| assert respuesta.status_code == 400 | |
| def test_un_ajuste_invalido_no_se_aplica(entorno): | |
| cliente, token, *_ = entorno | |
| cliente.post("/api/admin/login", json={"token": token}) | |
| assert cliente.patch( | |
| "/api/admin/settings", json={"retrieval": {"require_evidence": False}} | |
| ).status_code == 422 | |
| def test_un_ajuste_valido_se_aplica(entorno): | |
| cliente, token, *_ = entorno | |
| cliente.post("/api/admin/login", json={"token": token}) | |
| datos = cliente.patch("/api/admin/settings", json={"expression": {"expressiveness": 0.3}}).json() | |
| assert datos["expression"]["expressiveness"] == pytest.approx(0.3) | |
| def test_hay_que_reclamar_la_sesion_antes_de_hablar(entorno): | |
| cliente, token, _, sesion = entorno | |
| cliente.post("/api/admin/login", json={"token": token}) | |
| assert cliente.post("/api/admin/voice/ask", content=b"\x00\x00" * 800).status_code == 409 | |
| assert cliente.post("/api/admin/voice/claim").json()["active"] is True | |
| respuesta = cliente.post("/api/admin/voice/ask", content=b"\x00\x00" * 8000) | |
| assert respuesta.status_code == 200 | |
| assert respuesta.headers["content-type"] == "audio/wav" | |
| assert respuesta.content[:4] == b"RIFF" | |
| cliente.post("/api/admin/voice/release") | |
| assert sesion.active is False | |
| def test_el_registro_se_puede_leer(entorno): | |
| cliente, token, *_ = entorno | |
| cliente.post("/api/admin/login", json={"token": token}) | |
| from lexia.core.logging import log | |
| log("prueba_de_registro", valor=1) | |
| datos = cliente.get("/api/admin/logs?lines=50").json() | |
| assert any("prueba_de_registro" in linea for linea in datos["lines"]) | |
| assert all(json.loads(linea) for linea in datos["lines"]) | |
| def test_el_panel_expone_las_metricas_de_recuperacion(entorno): | |
| """Separar recuperar de redactar es lo que hace accionable una queja.""" | |
| cliente, token, *_ = entorno | |
| respuesta = cliente.get("/api/admin/retrieval?days=7", headers={"x-lexia-token": token}) | |
| assert respuesta.status_code == 200 | |
| datos = respuesta.json() | |
| assert {"consultas", "etapas", "abstenciones", "evidencia_media"} <= set(datos) | |
| def test_las_metricas_de_recuperacion_piden_token(entorno): | |
| cliente, *_ = entorno | |
| assert cliente.get("/api/admin/retrieval").status_code == 401 | |