chiforge / server /utils.py
SanketAI's picture
Upload folder using huggingface_hub
cca9a63 verified
Raw History Blame Contribute Delete
2.54 kB
"""
Helper utilities for the ChipForge server environment.
"""
import json
import subprocess
from pathlib import Path
from typing import Any, Dict, List
from .constants import TASKS_DIR, TOOL_TIMEOUT
def discover_tasks() -> List[Path]:
"""Return sorted list of task directories under TASKS_DIR (recursive)."""
if not TASKS_DIR.is_dir():
return []
return sorted(
p.parent
for p in TASKS_DIR.rglob("task.json")
if p.is_file() and p.parent.is_dir()
)
def categorize_tasks(tasks: List[Path]) -> Dict[str, List[Path]]:
"""Organize tasks into difficulty categories."""
categorized_tasks = {"easy": [], "medium": [], "hard": []}
for task in tasks:
try:
with open(task / "task.json", "r") as f:
meta = json.load(f)
diff = meta.get("difficulty", "medium").lower()
if diff in categorized_tasks:
categorized_tasks[diff].append(task)
else:
categorized_tasks["medium"].append(task)
except Exception:
categorized_tasks["medium"].append(task)
return categorized_tasks
def run_tool(cmd: List[str], cwd: str, timeout: int = TOOL_TIMEOUT) -> Dict[str, Any]:
"""Run a shell command and return stdout, stderr, returncode."""
try:
result = subprocess.run(
cmd,
cwd=cwd,
capture_output=True,
text=True,
timeout=timeout,
)
return {
"stdout": result.stdout,
"stderr": result.stderr,
"returncode": result.returncode,
}
except subprocess.TimeoutExpired:
return {
"stdout": "",
"stderr": f"Command timed out after {timeout}s",
"returncode": -1,
}
except FileNotFoundError as e:
return {
"stdout": "",
"stderr": f"Tool not found: {e}",
"returncode": -1,
}
def extract_error_summary(stderr: str, stdout: str = "") -> str:
"""Extract a one-line error summary from tool output."""
combined = stderr + "\n" + stdout
for line in combined.splitlines():
line = line.strip()
if not line:
continue
lower = line.lower()
if any(kw in lower for kw in ("error", "syntax", "warning", "latch", "fail")):
return line[:200]
for line in stderr.splitlines():
line = line.strip()
if line:
return line[:200]
return ""