"""Read-only account-context model pilot. Never creates projects, runs, or subscriptions.

python scripts/pilot_project_discovery.py --email user@example.com --out .pytest_tmp/discovery-pilot
Optional --answers-json is a JSON array of scripted user answers after the initial prompt.
Trace files contain prompts and model responses, but never API keys or HTTP headers.
"""

import argparse
import asyncio
import json
import sys
import time
from pathlib import Path

sys.path.insert(0, str(Path(__file__).resolve().parents[1]))

from sqlalchemy import text
from src.config import get_settings
from src.core.database import async_session_factory, engine
from src.domain.projects.discovery_catalog import build_discovery_payload
from src.domain.projects.discovery_service import available_templates
from src.integrations.project_intake_client import discover_project

DEFAULT_PROMPT = (
    "Build a SaaS MVP with email login, onboarding, a customer dashboard, "
    "Stripe subscriptions and an admin panel for managing accounts."
)


async def main(args):
    settings = get_settings()
    if args.timeout:
        settings = settings.model_copy(update={"project_intake_timeout_seconds": args.timeout})
    engine.echo = False
    async with async_session_factory() as db:
        await db.execute(text("SET TRANSACTION READ ONLY"))
        rows = (
            (
                await db.execute(
                    text("""
            SELECT u.id AS user_id, w.id AS workspace_id, w.name, w.selected_plan_slug,
                   s.status AS subscription_status, s.plan_slug
            FROM users u JOIN workspace_memberships m ON m.user_id=u.id
            JOIN workspaces w ON w.id=m.workspace_id
            LEFT JOIN LATERAL (SELECT status,plan_slug FROM subscriptions
                WHERE workspace_id=w.id ORDER BY created_at DESC LIMIT 1) s ON true
            WHERE lower(u.email)=lower(:email)
        """),
                    {"email": args.email},
                )
            )
            .mappings()
            .all()
        )
        if args.workspace_id:
            rows = [row for row in rows if str(row["workspace_id"]) == args.workspace_id]
        if len(rows) != 1:
            raise ValueError("Select exactly one account workspace with --workspace-id")
        account = dict(rows[0])
        templates = await available_templates(db, account["workspace_id"])
        payload = build_discovery_payload("nuxt_app", "generated", {"messages": []}, templates)
        await db.rollback()
    await engine.dispose()
    output = Path(args.out).resolve()
    output.mkdir(parents=True, exist_ok=True)
    inputs = [args.prompt]
    if args.answers_json:
        inputs.extend(json.loads(Path(args.answers_json).read_text(encoding="utf-8")))
    from src.domain.billing.normalization import requires_payment_flag

    report = {
        "account": account,
        "mode": "internal_read_only_model_pilot",
        "production_billing_would_allow": not requires_payment_flag(
            account["subscription_status"] or "none", account["selected_plan_slug"]
        ),
        "model": settings.project_intake_model,
        "timeout_seconds": settings.project_intake_timeout_seconds,
        "template_candidates": len(payload["templates"]),
        "turns": [],
    }
    state = {"messages": [], "version": 0, "status": "pending", "result": None}
    for index, message in enumerate(inputs, start=1):
        state["messages"] = [
            *state["messages"],
            {"role": "user", "content": message},
        ]
        state["latest_input"] = {"type": "message", "content": message}
        state["version"] = index
        payload = build_discovery_payload("nuxt_app", "generated", state, templates)
        trace = {"turn": index, "scripted_answer": index > 1}
        start = time.monotonic()
        try:
            result = await asyncio.wait_for(
                discover_project(payload, settings, trace=trace),
                timeout=settings.project_intake_timeout_seconds,
            )
            from src.domain.projects.discovery_readiness import (
                discovery_assistant_message,
                finalize_discovery_result,
            )

            trace["raw_result"] = result.model_dump()
            result = finalize_discovery_result(result, payload)
            trace["result"] = result.model_dump()
            payload["messages"].append(
                {
                    "role": "assistant",
                    "content": discovery_assistant_message(result),
                }
            )
            state["messages"] = payload["messages"]
            state["result"] = result.model_dump()
            state["status"] = result.decision
            state["core_blockers"] = list(result.readiness.blocking_decision_ids)
        except Exception as exc:
            trace["error_type"] = type(exc).__name__
        trace["elapsed_seconds"] = round(time.monotonic() - start, 3)
        trace_file = output / f"turn-{index:02}.json"
        trace_file.write_text(
            json.dumps(trace, indent=2, default=str, ensure_ascii=False), encoding="utf-8"
        )
        report["turns"].append(
            {
                "trace": str(trace_file),
                "elapsed_seconds": trace["elapsed_seconds"],
                "error_type": trace.get("error_type"),
                "result": trace.get("result"),
            }
        )
        print(json.dumps(report["turns"][-1], ensure_ascii=False))
        if trace.get("error_type"):
            break
    (output / "report.json").write_text(
        json.dumps(report, indent=2, default=str, ensure_ascii=False), encoding="utf-8"
    )
    return 1 if any(t.get("error_type") for t in report["turns"]) else 0


if __name__ == "__main__":
    parser = argparse.ArgumentParser(description=__doc__)
    parser.add_argument("--email", required=True)
    parser.add_argument("--workspace-id")
    parser.add_argument("--out", required=True)
    parser.add_argument("--prompt", default=DEFAULT_PROMPT)
    parser.add_argument("--answers-json")
    parser.add_argument(
        "--timeout", type=float, help="Diagnostic-only override; does not change app settings"
    )
    args = parser.parse_args()
    try:
        raise SystemExit(asyncio.run(main(args)))
    except Exception as exc:
        print(
            json.dumps(
                {
                    "error_type": type(exc).__name__,
                    "phase": "pilot_setup",
                    "file": getattr(exc, "filename", None),
                }
            )
        )
        raise SystemExit(1) from None
