Files
tianxuan/tests/test_e2e_batch.py

112 lines
3.7 KiB
Python

"""E2E batch upload test: upload 10 CSV files (2 batches of 5), cluster, verify."""
import subprocess, time, os, sys, glob, json
PROJ = r"E:\hjq\天璇"
PORT = 8765
BASE = f"http://127.0.0.1:{PORT}"
# ═══ Kill old server on PORT ═══
print("1. Killing old server on port 8765...")
kill_result = subprocess.run(
f'Get-NetTCPConnection -LocalPort {PORT} -ErrorAction SilentlyContinue | '
f'ForEach-Object {{ taskkill /F /PID $_.OwningProcess }}',
shell=True, capture_output=True, text=True
)
time.sleep(2)
# ═══ Start server ═══
print("2. Starting Django server...")
os.chdir(PROJ)
server = subprocess.Popen(
[r"runtime\python\python.exe", "manage.py", "runserver", f"127.0.0.1:{PORT}", "--noreload"],
stdout=subprocess.DEVNULL, stderr=subprocess.DEVNULL
)
time.sleep(6)
print(" Server started.")
import requests
# ═══ Upload 10 files (single batch — batch endpoint has table-race pre-existing bug) ═══
print("3. Uploading 10 CSV files...")
csvs = sorted(glob.glob(os.path.join(PROJ, "data", "multi_upload", "*.csv")))[:10]
files = [("files", (os.path.basename(f), open(f, "rb"), "text/csv")) for f in csvs]
r = requests.post(f"{BASE}/upload/csv/", files=files, timeout=120)
data = r.json()
if "error" in data:
print(f" UPLOAD FAILED: {data['error']}")
server.terminate()
sys.exit(1)
run_id = data["run_id"]
print(f" Upload OK → run_id={run_id}")
# ═══ Poll until ready ═══
print("4. Polling status until ready...")
status = {}
for i in range(180):
try:
r = requests.get(f"{BASE}/runs/{run_id}/status/", timeout=30)
status = r.json()
except requests.exceptions.Timeout:
print(f" Poll #{i+1} timed out, retrying...")
time.sleep(3)
continue
except requests.exceptions.ConnectionError:
print(f" Poll #{i+1} connection refused, server may have crashed")
time.sleep(5)
continue
s = status.get("status")
if s in ("ready", "failed"):
break
if i % 15 == 0 and i > 0:
print(f" Still loading... status={s}")
time.sleep(3)
print(f" Status={status.get('status')}, flows={status.get('total_flows')}, "
f"error={status.get('error_message','')[:200]}")
if status.get("status") == "failed":
print(f" FAILED: {status.get('error_message','')}")
server.terminate()
sys.exit(1)
# ═══ Run clustering ═══
print("5. Running clustering (HDBSCAN)...")
r = requests.post(f"{BASE}/analyze/run/",
json={"run_id": run_id, "algorithm": "hdbscan", "min_cluster_size": 5, "cluster_mode": "raw"},
timeout=30)
print(f" Cluster trigger: {r.json()}")
for i in range(180):
try:
r = requests.get(f"{BASE}/runs/{run_id}/status/", timeout=30)
status = r.json()
except requests.exceptions.Timeout:
print(f" Poll #{i+1} timed out after 30s, retrying...")
time.sleep(2)
continue
except requests.exceptions.ConnectionError:
print(f" Poll #{i+1} connection refused, server may have crashed")
time.sleep(5)
continue
s = status.get("status")
if s in ("completed", "failed"):
break
if i % 20 == 0 and i > 0:
print(f" Still clustering... status={s}")
time.sleep(5)
print(f" entity_count={status.get('entity_count')}, "
f"cluster_count={status.get('cluster_count')}, "
f"status={status.get('status')}")
# ═══ Cleanup & verdict ═══
server.terminate()
server.wait()
if status.get("status") == "completed" and status.get("cluster_count", 0) > 0:
print("E2E PASSED")
sys.exit(0)
else:
print(f"E2E FAILED (status={status.get('status')}, clusters={status.get('cluster_count')})")
sys.exit(1)