Spaces:
Sleeping
Sleeping
| from __future__ import annotations | |
| from collections.abc import Generator | |
| import pytest | |
| from fastapi.testclient import TestClient | |
| from app.core.config import Settings | |
| from app.main import create_app | |
| from app.ml.model_manager import ModelPrediction | |
| class FakeModelManager: | |
| def __init__(self) -> None: | |
| self.loaded = False | |
| self.version = "fake-1.0.0" | |
| def is_loaded(self) -> bool: | |
| return self.loaded | |
| def model_version(self) -> str: | |
| return self.version | |
| def load_model(self) -> None: | |
| self.loaded = True | |
| def unload_model(self) -> None: | |
| self.loaded = False | |
| def predict_one(self, input_data: dict) -> ModelPrediction: | |
| label = ">50K" if input_data["education_num"] >= 13 and input_data["hours_per_week"] >= 40 else "<=50K" | |
| probability = 0.91 if label == ">50K" else 0.24 | |
| return ModelPrediction( | |
| label=label, | |
| probability=probability, | |
| raw_probabilities=[1 - probability, probability], | |
| model_version=self.version, | |
| ) | |
| def build_test_settings(database_url: str, **overrides) -> Settings: | |
| base_values = { | |
| "environment": "test", | |
| "debug": False, | |
| "docs_enabled": True, | |
| "database_url": database_url, | |
| "jwt_secret_key": "test-secret-key-32-characters-minimum", | |
| "allowed_hosts": ["testserver", "localhost", "127.0.0.1", "*.hf.space", "*.huggingface.co"], | |
| "cors_allow_origins": ["http://testserver"], | |
| "rate_limit_enabled": True, | |
| "rate_limit_requests": 50, | |
| "rate_limit_window_seconds": 60, | |
| "auto_seed_admin": False, | |
| "seed_admin_email": None, | |
| "seed_admin_password": None, | |
| } | |
| return Settings(**(base_values | overrides)) | |
| def app(tmp_path) -> Generator: | |
| db_path = tmp_path / "test_api.db" | |
| settings = build_test_settings(f"sqlite:///{db_path}") | |
| application = create_app(settings=settings, model_manager=FakeModelManager()) | |
| yield application | |
| def client(app) -> Generator[TestClient, None, None]: | |
| with TestClient(app) as test_client: | |
| yield test_client | |
| def auth_token(client: TestClient) -> str: | |
| registration_payload = { | |
| "email": "user@example.com", | |
| "full_name": "Test User", | |
| "password": "StrongPass!123", | |
| } | |
| client.post("/api/v1/auth/register", json=registration_payload) | |
| response = client.post( | |
| "/api/v1/auth/login", | |
| json={"email": registration_payload["email"], "password": registration_payload["password"]}, | |
| ) | |
| return response.json()["access_token"] | |
| def auth_headers(auth_token: str) -> dict[str, str]: | |
| return {"Authorization": f"Bearer {auth_token}"} | |
| def valid_prediction_payload() -> dict[str, object]: | |
| return { | |
| "age": 45, | |
| "workclass": "Private", | |
| "fnlwgt": 250000, | |
| "education": "Masters", | |
| "education.num": 14, | |
| "marital.status": "Married-civ-spouse", | |
| "occupation": "Exec-managerial", | |
| "relationship": "Husband", | |
| "race": "White", | |
| "sex": "Male", | |
| "capital.gain": 15000, | |
| "capital.loss": 0, | |
| "hours.per.week": 50, | |
| "native.country": "United-States", | |
| } | |