Files
Wictionary-Data-Parser/tests/test_framework.py
2026-02-13 00:10:40 +01:00

229 lines
7.9 KiB
Python

#!/usr/bin/env python3
"""
wikParse Test Framework
=======================
Comprehensive testing framework for all wikParse components.
"""
import json
import os
import sys
import tempfile
import sqlite3
import pathlib
from typing import Dict, List, Any, Optional
# Add scripts directory to path
SCRIPT_DIR = pathlib.Path(__file__).parent.parent / "scripts"
sys.path.insert(0, str(SCRIPT_DIR))
from transform_wiktionary import WiktionaryTransformer
from InflectionProcessor import InflectionProcessor, UniversalInflectionCompressor
class TestFramework:
"""Base test framework with common utilities."""
def __init__(self):
self.test_results = {
"passed": 0,
"failed": 0,
"errors": [],
"warnings": []
}
self.temp_files = []
def assert_equal(self, actual, expected, message=""):
"""Assert that two values are equal."""
if actual == expected:
self.test_results["passed"] += 1
return True
else:
self.test_results["failed"] += 1
error_msg = f"Assertion failed: {message}"
error_msg += f"\n Expected: {expected}"
error_msg += f"\n Actual: {actual}"
self.test_results["errors"].append(error_msg)
return False
def assert_not_equal(self, actual, expected, message=""):
"""Assert that two values are not equal."""
if actual != expected:
self.test_results["passed"] += 1
return True
else:
self.test_results["failed"] += 1
error_msg = f"Assertion failed: {message}"
error_msg += f"\n Values should not be equal but both are: {actual}"
self.test_results["errors"].append(error_msg)
return False
def assert_true(self, condition, message=""):
"""Assert that a condition is true."""
if condition:
self.test_results["passed"] += 1
return True
else:
self.test_results["failed"] += 1
error_msg = f"Assertion failed: {message}"
error_msg += f"\n Condition is False"
self.test_results["errors"].append(error_msg)
return False
def assert_false(self, condition, message=""):
"""Assert that a condition is false."""
if not condition:
self.test_results["passed"] += 1
return True
else:
self.test_results["failed"] += 1
error_msg = f"Assertion failed: {message}"
error_msg += f"\n Condition is True"
self.test_results["errors"].append(error_msg)
return False
def assert_is_instance(self, obj, cls, message=""):
"""Assert that an object is an instance of a class."""
if isinstance(obj, cls):
self.test_results["passed"] += 1
return True
else:
self.test_results["failed"] += 1
error_msg = f"Assertion failed: {message}"
error_msg += f"\n Expected type: {cls}"
error_msg += f"\n Actual type: {type(obj)}"
self.test_results["errors"].append(error_msg)
return False
def assert_in(self, member, container, message=""):
"""Assert that a member is in a container."""
if member in container:
self.test_results["passed"] += 1
return True
else:
self.test_results["failed"] += 1
error_msg = f"Assertion failed: {message}"
error_msg += f"\n Member not found in container"
self.test_results["errors"].append(error_msg)
return False
def assert_not_in(self, member, container, message=""):
"""Assert that a member is not in a container."""
if member not in container:
self.test_results["passed"] += 1
return True
else:
self.test_results["failed"] += 1
error_msg = f"Assertion failed: {message}"
error_msg += f"\n Member found in container but should not be"
self.test_results["errors"].append(error_msg)
return False
def create_temp_file(self, content="", suffix=".json"):
"""Create a temporary file and return its path."""
temp_file = tempfile.NamedTemporaryFile(mode='w', suffix=suffix, delete=False)
if content:
temp_file.write(content)
temp_file.close()
self.temp_files.append(temp_file.name)
return temp_file.name
def cleanup(self):
"""Clean up temporary files."""
for file_path in self.temp_files:
try:
os.unlink(file_path)
except:
pass
self.temp_files = []
def print_summary(self):
"""Print test summary."""
total = self.test_results["passed"] + self.test_results["failed"]
print("\n" + "="*60)
print("TEST SUMMARY")
print("="*60)
print(f"Total tests: {total}")
print(f"Passed: {self.test_results['passed']}")
print(f"Failed: {self.test_results['failed']}")
if total > 0:
success_rate = (self.test_results['passed'] / total) * 100
print(f"Success rate: {success_rate:.1f}%")
if self.test_results['errors']:
print(f"\nErrors: {len(self.test_results['errors'])}")
for error in self.test_results['errors']:
print(f" - {error}")
if self.test_results['warnings']:
print(f"\nWarnings: {len(self.test_results['warnings'])}")
for warning in self.test_results['warnings']:
print(f" - {warning}")
return self.test_results["failed"] == 0
class SchemaValidator:
"""Schema validation utilities."""
@staticmethod
def validate_universal_schema(entry: Dict[str, Any]) -> bool:
"""Validate an entry against the universal schema."""
required_fields = ["word", "pos", "senses"]
# Check required fields
for field in required_fields:
if field not in entry:
return False
# Check field types
if not isinstance(entry["word"], str):
return False
if not isinstance(entry["pos"], str):
return False
if not isinstance(entry["senses"], list):
return False
# Validate senses structure
for sense in entry["senses"]:
if not isinstance(sense, dict):
return False
return True
class TestDataLoader:
"""Load test data from various sources."""
@staticmethod
def load_sample_data(sample_name: str) -> Dict[str, Any]:
"""Load sample data from samples directory."""
samples_dir = pathlib.Path(__file__).parent.parent / "samples"
# Try different paths
possible_paths = [
samples_dir / "german" / f"{sample_name}.json",
samples_dir / "french" / f"{sample_name}.json",
samples_dir / f"{sample_name}.json"
]
for path in possible_paths:
if path.exists():
with open(path, 'r', encoding='utf-8') as f:
return json.load(f)
raise FileNotFoundError(f"Sample data not found: {sample_name}")
@staticmethod
def load_jsonl_data(file_path: str) -> List[Dict[str, Any]]:
"""Load JSONL data from file."""
entries = []
with open(file_path, 'r', encoding='utf-8') as f:
for line in f:
if line.strip():
entries.append(json.loads(line.strip()))
return entries
if __name__ == "__main__":
print("wikParse Test Framework")
print("Run specific test modules instead of this framework directly.")