Spaces:
Sleeping
Sleeping
| #!/usr/bin/env python | |
| # -*- coding: utf-8 -*- | |
| """ | |
| Cloud tests for CarsRUS Space on Hugging Face. | |
| Runs against: https://huggingface.co/spaces/galbendavids/CarsRUS | |
| Requires: pip install gradio_client | |
| Run: PYTHONPATH=. python tests/test_cloud.py | |
| or: bash tests/run_cloud_tests.sh | |
| """ | |
| import os | |
| import sys | |
| _tests_dir = os.path.dirname(os.path.abspath(__file__)) | |
| _project_root = os.path.dirname(_tests_dir) | |
| if _project_root not in sys.path: | |
| sys.path.insert(0, _project_root) | |
| # Space URL (public Space โ no token needed for read) | |
| SPACE_URL = os.environ.get("CARSRUS_SPACE_URL", "galbendavids/CarsRUS") | |
| def get_client(): | |
| """Create Gradio client for the Space. Uses HF token from env if set.""" | |
| try: | |
| from gradio_client import Client | |
| except ImportError: | |
| print("โ gradio_client not installed. Run: pip install gradio_client") | |
| sys.exit(1) | |
| hf_token = os.environ.get("HF_TOKEN") or os.environ.get("HUGGING_FACE_HUB_TOKEN") | |
| return Client(SPACE_URL, hf_token=hf_token or None) | |
| def collect_chat_response(client, message: str): | |
| """Call the chat endpoint and return the full response (streaming collected).""" | |
| # Space API: predict(message, api_name="/chat") -> response (str) | |
| result = client.predict(message, api_name="/chat") | |
| return result | |
| def test_space_reachable(): | |
| """Space is up and client can connect.""" | |
| print("\n[Cloud] test_space_reachable...") | |
| client = get_client() | |
| # Just ensure we can get API info (view_api or similar) | |
| try: | |
| api_info = client.view_api() | |
| print(f" Endpoints: {list(api_info.get('named_endpoints', api_info) if isinstance(api_info, dict) else 'ok')}") | |
| except Exception as e: | |
| print(f" view_api: {e}") | |
| print("โ test_space_reachable passed") | |
| return client | |
| def test_chat_supported_car(client): | |
| """Ask about a supported car (e.g. Audi RS3) โ expect substantive answer, no config error.""" | |
| print("\n[Cloud] test_chat_supported_car...") | |
| message = "Tell me about the Audi RS3" | |
| try: | |
| result = collect_chat_response(client, message) | |
| except Exception as e: | |
| print(f" Call failed: {e}") | |
| try: | |
| api = client.view_api() | |
| print(f" API: {api}") | |
| except Exception: | |
| pass | |
| raise | |
| text = result if isinstance(result, str) else str(result) | |
| # Should not be config/init error | |
| assert "Configuration Error" not in text and "Initialization Error" not in text, ( | |
| f"Expected normal answer, got: {text[:200]}" | |
| ) | |
| # Should mention something about the car or content | |
| assert len(text.strip()) > 50, f"Response too short: {text[:200]}" | |
| print(f" Response length: {len(text)} chars") | |
| print("โ test_chat_supported_car passed") | |
| def test_chat_unsupported_car(client): | |
| """Ask about an unsupported car โ expect refusal or supported list.""" | |
| print("\n[Cloud] test_chat_unsupported_car...") | |
| message = "What do you think about BMW X5?" | |
| try: | |
| result = collect_chat_response(client, message) | |
| except Exception as e: | |
| print(f" Call failed: {e}") | |
| raise | |
| text = result if isinstance(result, str) else str(result) | |
| assert "Configuration Error" not in text and "Initialization Error" not in text | |
| # Refusal or supported list | |
| has_refusal = ( | |
| "not in my knowledge" in text.lower() | |
| or "ืื ื ืืฆื" in text | |
| or "supported" in text.lower() | |
| or "ื ืชืืืื" in text | |
| or "Citroen" in text | |
| or "Audi RS3" in text | |
| ) | |
| assert has_refusal or len(text) > 20, f"Expected refusal/supported list, got: {text[:300]}" | |
| print("โ test_chat_unsupported_car passed") | |
| def test_chat_comparison(client): | |
| """Ask to compare two supported cars โ expect comparison content.""" | |
| print("\n[Cloud] test_chat_comparison...") | |
| message = "Compare Audi RS3 vs Hyundai Elantra N" | |
| try: | |
| result = collect_chat_response(client, message) | |
| except Exception as e: | |
| print(f" Call failed: {e}") | |
| raise | |
| text = result if isinstance(result, str) else str(result) | |
| assert "Configuration Error" not in text and "Initialization Error" not in text | |
| assert len(text.strip()) > 30, f"Response too short: {text[:200]}" | |
| print("โ test_chat_comparison passed") | |
| def test_chat_hebrew(client): | |
| """Hebrew query โ app should respond (Hebrew or English).""" | |
| print("\n[Cloud] test_chat_hebrew...") | |
| message = "ืกืคืจ ืื ืขื ืืืื RS3" | |
| try: | |
| result = collect_chat_response(client, message) | |
| except Exception as e: | |
| print(f" Call failed: {e}") | |
| raise | |
| text = result if isinstance(result, str) else str(result) | |
| assert "Configuration Error" not in text and "Initialization Error" not in text | |
| assert len(text.strip()) > 20, f"Response too short: {text[:200]}" | |
| print("โ test_chat_hebrew passed") | |
| def test_chat_link_co_01(client): | |
| """Link & Co 01 is in the knowledge base โ must NOT say 'not in my knowledge'.""" | |
| print("\n[Cloud] test_chat_link_co_01...") | |
| for message in ["ืกืคืจ ืขื ืืื ืง ืื ื ืงื 01", "Tell me about Link and Co 01"]: | |
| try: | |
| result = collect_chat_response(client, message) | |
| except Exception as e: | |
| print(f" Call failed for {message!r}: {e}") | |
| raise | |
| text = result if isinstance(result, str) else str(result) | |
| assert "Configuration Error" not in text and "Initialization Error" not in text | |
| assert "not in my knowledge" not in text and "ืื ื ืืฆื ืืืกืืก ืืืืข" not in text, ( | |
| f"Link & Co 01 is in scraped_data (link-and-co-01-2026); got refusal: {text[:300]}" | |
| ) | |
| assert len(text.strip()) > 50, f"Response too short for {message!r}: {text[:200]}" | |
| print("โ test_chat_link_co_01 passed") | |
| def run_all(): | |
| """Run all cloud tests. Exit 0 if all pass.""" | |
| print("=" * 60) | |
| print("CarsRUS โ Cloud tests") | |
| print(f"Space: {SPACE_URL}") | |
| print("=" * 60) | |
| try: | |
| client = test_space_reachable() | |
| test_chat_supported_car(client) | |
| test_chat_unsupported_car(client) | |
| test_chat_comparison(client) | |
| test_chat_hebrew(client) | |
| test_chat_link_co_01(client) | |
| except Exception as e: | |
| print(f"\nโ Cloud test failed: {e}") | |
| import traceback | |
| traceback.print_exc() | |
| return 1 | |
| print("\nโ All cloud tests passed.") | |
| return 0 | |
| if __name__ == "__main__": | |
| sys.exit(run_all()) | |