"""C2 extra (NOT the verdict method): full payloads, original vs Headroom-compressed, with the hosted models.
Inputs: ../payloads/{synthetic_logs,wiki_search}.json (original, as sent to compress() in c1b/c2a) and
../payloads/*.compressed.txt (Headroom 0.41.0 output, byte-identical to c1b/c2a). Questions = the 5 C2a questions per payload
(07-c2a-retention.py), answers computed by code from the original. Because of the 50 req/day free limit, the 5 questions are
asked in ONE request per input (numbered answers) instead of one request per question. Same norm() scoring as c2b.
usage: python c2_hosted_full.py OUT.json MODEL_ID"""
import json, sys, time, os, re, urllib.request, urllib.error
P = "../payloads/"; OUT, MODEL = sys.argv[1], sys.argv[2]
lg = json.load(open(P + "synthetic_logs.json")); wk = json.load(open(P + "wiki_search.json"))
fatal = next(x for x in lg if x["level"] == "FATAL")
Q = {
 "synthetic_logs": [("What is the msg of the FATAL entry?", fatal["msg"]), ("What is the request_id of the FATAL entry?", fatal["request_id"]),
   ("What is the latency_ms of request %s?" % lg[500]["request_id"], str(lg[500]["latency_ms"])),
   ("Which service logged the entry with ts %s?" % lg[1999]["ts"], lg[1999]["service"]),
   ("How many entries have level ERROR?", str(sum(1 for x in lg if x["level"] == "ERROR")))],
 "wiki_search": [("What is the title of the very first result?", wk[0]["title"]), ("What is the pageid of the article titled '%s'?" % wk[49]["title"], str(wk[49]["pageid"])),
   ("What is the wordcount of the article titled '%s'?" % wk[149]["title"], str(wk[149]["wordcount"])),
   ("What is the snippet of the article titled '%s'? Copy it exactly." % wk[3]["title"], wk[3]["snippet"]),
   ("How many results have wordcount greater than 5000?", str(sum(1 for x in wk if x["wordcount"] > 5000)))],
}
KEY = os.environ["OPENROUTER_API_KEY"]; REQS = {"n": 0}
def ask(ctx, qs):
    prompt = "Tool output:\n" + ctx + "\n\nQuestions:\n" + "\n".join("%d. %s" % (i + 1, q) for i, (q, _) in enumerate(qs)) + \
             "\nAnswer each question with only the value, nothing else, one per line, in the form '1. value'."
    body = {"model": MODEL, "messages": [{"role": "user", "content": prompt}], "temperature": 0, "seed": 1, "max_tokens": 16000}
    for attempt in range(3):
        REQS["n"] += 1; t = time.time()
        try:
            req = urllib.request.Request("https://openrouter.ai/api/v1/chat/completions", data=json.dumps(body).encode(),
                  headers={"Content-Type": "application/json", "Authorization": "Bearer " + KEY, "X-Title": "triedagents try-tools C2 rerun"})
            o = json.load(urllib.request.urlopen(req, timeout=900))
            if "choices" not in o: raise RuntimeError(json.dumps(o)[:300])
            return (o["choices"][0]["message"].get("content") or "").strip(), (o.get("usage") or {}).get("prompt_tokens"), round(time.time() - t, 1), o.get("model"), o.get("provider"), attempt
        except urllib.error.HTTPError as e:
            print("HTTP", e.code, e.read().decode(errors="replace")[:300], file=sys.stderr, flush=True)
            if e.code == 429: time.sleep(40 * (attempt + 1)); continue
            raise
    raise RuntimeError("gave up")
def norm(s): return re.sub(r"[\s'\"`.]+", "", s).lower()
def parse(text, n):
    ans = [""] * n
    for line in text.splitlines():
        m = re.match(r"\s*(\d+)[.)]\s*(.*)", line)
        if m and 1 <= int(m.group(1)) <= n and not ans[int(m.group(1)) - 1]: ans[int(m.group(1)) - 1] = m.group(2).strip()
    return ans
out = json.load(open(OUT)) if os.path.exists(OUT) else {"model": MODEL, "via": "OpenRouter free tier", "method": "full payloads, 5 questions batched per request; see docstring", "payloads": {}}
for name, qs in Q.items():
    raw = open(P + name + ".json").read(); c = open(P + name + ".compressed.txt").read(); c = json.loads(c) if c.startswith('"') else c
    rec = out["payloads"].setdefault(name, {"ccr_markers_in_compressed": c.count("<<ccr:"), "runs": {}})
    for label, ctx in (("original", raw), ("compressed", c)):
        if label in rec["runs"]: continue
        txt, pt, s, served, prov, retries = ask(ctx, qs)
        ans = parse(txt, len(qs))
        res = [{"q": q, "truth": a[:300], "model": m[:300], "correct": norm(a) == norm(m) or (norm(a) in norm(m) and len(norm(m)) <= len(norm(a)) + 12)} for (q, a), m in zip(qs, ans)]
        rec["runs"][label] = {"correct": sum(x["correct"] for x in res), "of": len(qs), "prompt_tokens": pt, "seconds": s, "served_model": served, "provider": prov, "retries": retries, "raw_reply": txt[:3000], "questions": res}
        print(name, label, rec["runs"][label]["correct"], "/", len(qs), pt, s, [x["correct"] for x in res], flush=True)
        out["http_requests_this_process"] = REQS["n"]; json.dump(out, open(OUT, "w"), indent=1, ensure_ascii=False)
