60 lines
1.7 KiB
Python
Executable File
60 lines
1.7 KiB
Python
Executable File
#!/usr/bin/env python3
|
|
import argparse
|
|
import json
|
|
from pathlib import Path
|
|
from typing import Dict
|
|
|
|
|
|
def load_json(path: Path):
|
|
with path.open("r", encoding="utf-8") as f:
|
|
return json.load(f)
|
|
|
|
|
|
def main() -> int:
|
|
p = argparse.ArgumentParser(description="Aggregate closure ladder outcomes.")
|
|
p.add_argument("--runs-root", default="logs/taskitem_runs")
|
|
p.add_argument("--include-glob", default="TEST_ONLY_*closure_ladder*")
|
|
p.add_argument("--out", required=True)
|
|
args = p.parse_args()
|
|
|
|
root = Path(args.runs_root)
|
|
summaries = sorted(root.glob(f"{args.include_glob}/closure_ladder_summary.json"))
|
|
|
|
mode_counts: Dict[str, int] = {}
|
|
status_counts: Dict[str, int] = {}
|
|
rows = []
|
|
for s in summaries:
|
|
try:
|
|
j = load_json(s)
|
|
except Exception:
|
|
continue
|
|
mode = str(j.get("selected_mode", ""))
|
|
status = str(j.get("status", "unknown"))
|
|
mode_counts[mode] = mode_counts.get(mode, 0) + 1
|
|
status_counts[status] = status_counts.get(status, 0) + 1
|
|
rows.append({
|
|
"run_id": s.parent.name,
|
|
"status": status,
|
|
"selected_mode": mode,
|
|
"selected_run": str(j.get("selected_run", "")),
|
|
})
|
|
|
|
out = {
|
|
"status": "ok",
|
|
"record_count": len(rows),
|
|
"status_counts": status_counts,
|
|
"selected_mode_counts": mode_counts,
|
|
"records": rows,
|
|
}
|
|
|
|
with Path(args.out).open("w", encoding="utf-8") as f:
|
|
json.dump(out, f, indent=2, sort_keys=True)
|
|
f.write("\n")
|
|
|
|
print(json.dumps({"status": "ok", "record_count": len(rows), "out": args.out}, sort_keys=True))
|
|
return 0
|
|
|
|
|
|
if __name__ == "__main__":
|
|
raise SystemExit(main())
|