// ═══════════════════════════════════════════════════════════════════
// RAISABLE INTELLIGENCE — WORKSPACE
// Multi-tenant · multi-project context: tenants, projects, pipeline
// runs, generated documents. The Raisable Seed project is LIVE —
// backed by window.RAISABLE (KB, graph, dossier); other projects
// carry their own run state at earlier pipeline stages.
// ═══════════════════════════════════════════════════════════════════
(function () {
  const R = window.RAISABLE;

  // ── project lifecycle stages ───────────────────────────────────────
  const STAGES = {
    intake:     { label: "intake",     tone: "neutral", note: "artifacts arriving — pipeline not yet run" },
    comprehend: { label: "comprehend", tone: "info",    note: "parsing & knowledge build in progress" },
    research:   { label: "research",   tone: "info",    note: "deep research running" },
    drafting:   { label: "drafting",   tone: "warn",    note: "report composing — review gate ahead" },
    published:  { label: "published",  tone: "ok",      note: "intelligence report live" },
  };

  // ── run step statuses ──────────────────────────────────────────────
  const STEP_STATUS = {
    done:    { tone: "ok",      label: "done" },
    running: { tone: "accent",  label: "running" },
    queued:  { tone: "neutral", label: "queued" },
    blocked: { tone: "err",     label: "blocked" },
  };

  const TENANTS = [
    { id: "raisable", name: "Raisable Inc.",  short: "R", plan: "Enterprise", seats: 4, domain: "raisable.ai" },
    { id: "saxcap",   name: "SAXCAP",         short: "S", plan: "Growth",     seats: 7, domain: "saxcap.com" },
  ];

  // live metrics for the Raisable Seed project — computed from the KB
  const liveMetrics = (() => {
    if (!R) return {};
    const g = R.graph ? R.graph() : { nodes: [], edges: [] };
    const D = R.DOSSIER || {};
    const facts = R.KB.length;
    const srcCount = Object.keys(R.SRC).length;
    const verified = R.KB.filter((f) => f.cls === "V").length;
    const market = R.KB.filter((f) => f.group === "market").length;
    return {
      parse:      srcCount + " / " + srcCount + " sources parsed",
      extract:    facts + " datapoints extracted",
      kb:         facts + " memory keys · " + verified + " verified",
      kg:         g.nodes.length + " entities · " + g.edges.length + " edges",
      entity:     g.nodes.length + " entities resolved · deduped",
      oc_corp:    "WY register · ownership non-public",
      oc_ip:      "IP unregistered · work-for-hire",
      oc_customer:"comp ~4.1× verified · 55,162 EO 2024",
      background: g.nodes.length + " / " + g.nodes.length + " entities checked",
      crosscheck: (D.verification ? D.verification.length : 0) + " claims · " + (D.contradictions ? D.contradictions.length : 0) + " contradictions",
      market:     market + " market facts · classed A/H",
      gaps:       ((D.gaps && D.gaps.length) || 0) + " gaps registered",
      compose_brief:     "verdict · thesis · findings · risks",
      compose_passport:  "business · offering · financial model",
      compose_intel:     "verification · contradictions · gaps · sources",
      compose_strategic: "gates · actions · opportunity register",
      review:     "reviewer · V. Gudzenko — sign-off date GAP",
      publish:    "v3 → Document Library",
    };
  })();

  const PROJECTS = [
    {
      id: "raisable-seed", tenant: "raisable", name: "Raisable Inc. — Seed Round",
      subject: "Raisable Inc. (issuer · self)", kind: "Offering dossier", kbFill: 0.86,
      stage: "published", opened: "May 28, 2026", lastRun: "Jun 18, 2026", live: true,
      run: { id: "RUN-016", trigger: "re-run · RPT-v3 / WFT-v2 — structural relations + per-type compose", started: "Jun 18 · 14:20", reviewer: "V. Gudzenko", version: "v5.1",
        steps: { parse: "done", extract: "done", kb: "done", kg: "done", entity: "done", background: "done", oc_corp: "done", crosscheck: "done", oc_ip: "done", market: "done", oc_customer: "done", gaps: "done", compose: "done", compose_brief: "done", compose_passport: "done", compose_intel: "done", compose_strategic: "done", review: "done", publish: "done" } },
      metrics: liveMetrics,
      extraArtifacts: [
        { id: "DOC-014", name: "Bylaws (draft)", kind: "docx", file: "uploads/2_Bylaws_Raisable.docx", status: "parsed", dp: 0, uploaded: "30 May", parsed: "30 May" },
        { id: "DOC-015", name: "Organizational Consent — Sole Director", kind: "docx", file: "uploads/3_Organizational_Consent_Sole_Director_Raisable.docx", status: "parsed", dp: 0, uploaded: "30 May", parsed: "30 May" },
      ],
      docs: [
        { id: "GEN-001", name: "Executive Brief · weekly",        type: "report",     v: "v5.1", status: "published", date: "Jun 18, 2026", by: "RUN-016 · composer-1", route: "report" },
        { id: "GEN-002", name: "Product Passport · monthly",       type: "report",     v: "v5.1", status: "published", date: "Jun 18, 2026", by: "RUN-016 · composer-1", route: "report" },
        { id: "GEN-003", name: "Intelligence Report · monthly",    type: "report",     v: "v5.1", status: "published", date: "Jun 18, 2026", by: "RUN-016 · composer-1", route: "report" },
        { id: "GEN-004", name: "Strategic Review · quarterly",     type: "report",     v: "v5.1", status: "published", date: "Jun 18, 2026", by: "RUN-016 · composer-1", route: "report" },
        { id: "GEN-005", name: "Offering Readiness Assessment",    type: "assessment", v: "v2", status: "final",     date: "Jun 8, 2026",  by: "RUN-012 · composer-1", href: "../../exports/Raisable Readiness Assessment.html" },
        { id: "GEN-006", name: "Investor Pitch — Brief · 5 slides",      type: "deck",       v: "v1", status: "final",     date: "Jun 6, 2026",  by: "RUN-011 · composer-1", href: "../../exports/Raisable C2 Pitch - Brief 5 slides.html" },
        { id: "GEN-007", name: "Investor Pitch — Full · 12 slides",      type: "deck",       v: "v1", status: "final",     date: "Jun 6, 2026",  by: "RUN-011 · composer-1", href: "../../exports/Raisable C2 Pitch - Full 12 slides.html" },
        { id: "GEN-008", name: "Market Research Memo — capital-formation rails", type: "memo", v: "v1", status: "draft",   date: "Jun 9, 2026",  by: "RUN-013 · research-2" },
      ],
    },
    {
      id: "lionsgate", tenant: "saxcap", name: "Lionsgate World Resort — Tokenization",
      subject: "SAXCAP, Inc. · Lionsgate World Resort, Orlando", kind: "Tokenization diligence", kbFill: 0.71, kbRef: "LIONSGATE", reportRef: "LionsgateReport",
      stage: "published", opened: "Jun 9, 2026", lastRun: "Jun 18, 2026",
      run: { id: "RUN-032", trigger: "re-run · RPT-v3 / WFT-v2 — structural relations + verification ledger", started: "Jun 18 · 15:05", reviewer: "J. Whitfield", version: "v2.1",
        steps: { parse: "done", extract: "done", kb: "done", kg: "done", background: "done", crosscheck: "done", market: "done", gaps: "done", compose: "done", compose_brief: "done", compose_passport: "done", compose_intel: "done", compose_strategic: "done", review: "done", publish: "done" } },
      metrics: { parse: "6 / 6 sources parsed", extract: "52 datapoints extracted", kb: "52 memory keys · 5 URL-verified", kg: "8 entities · 8 edges", background: "6 / 6 entities checked · 2 at risk", crosscheck: "12 claims · 6 contradictions · 4 URL-cited", market: "comps verified · per-cap gap flagged", gaps: "7 gaps registered · 3 block issuance", compose_brief: "verdict · thesis · 5 findings · 6 risks", compose_passport: "asset · deal · underwriting", compose_intel: "12 checks · 6 contradictions · 7 gaps", compose_strategic: "2 gates · 6 actions · opportunity register", review: "signed off · J. Whitfield · Jun 12", publish: "v1 → Document Library" },
      artifacts: [
        { id: "DECK",  name: "SAXCAP Lionsgate Pitch Deck (9 Jun 2026)", kind: "pdf",  file: "uploads/SAXCAP Lionsgate Deck 20260609.pdf", status: "parsed", dp: 29, uploaded: "9 Jun", parsed: "9 Jun" },
        { id: "MODEL", name: "Financial Model (slides 9–13)",            kind: "xlsx", file: "deck · DCF & sources-and-uses",                 status: "parsed", dp: 12, uploaded: "9 Jun", parsed: "10 Jun" },
        { id: "VISIT", name: "Visit Orlando 2024 data",                  kind: "html", file: "web capture · visitorlando.com",               status: "parsed", dp: 4, parsed: "11 Jun" },
        { id: "WIKI",  name: "Public records — LEWO · Skyplex · principals", kind: "html", file: "web capture · press & filings",             status: "parsed", dp: 5, parsed: "11 Jun" },
        { id: "OBJ",   name: "Orlando Business Journal (Skyplex)",        kind: "html", file: "web capture · bizjournals.com",               status: "parsed", dp: 2, parsed: "11 Jun" },
        { id: "UPR",   name: "United Parks & Resorts FY2024 results",     kind: "pdf",  file: "public · SEC / IR",                          status: "parsed", dp: 1, parsed: "11 Jun" },
      ],
      docs: [
        { id: "GEN-101", name: "Executive Brief · weekly",        type: "report", v: "v2.1", status: "published", date: "Jun 18, 2026", by: "RUN-032 · composer-1", route: "report" },
        { id: "GEN-102", name: "Product Passport · monthly",      type: "report", v: "v2.1", status: "published", date: "Jun 18, 2026", by: "RUN-032 · composer-1", route: "report" },
        { id: "GEN-103", name: "Intelligence Report · monthly",   type: "report", v: "v2.1", status: "published", date: "Jun 18, 2026", by: "RUN-032 · composer-1", route: "report" },
        { id: "GEN-104", name: "Strategic Review · quarterly",    type: "report", v: "v2.1", status: "published", date: "Jun 18, 2026", by: "RUN-032 · composer-1", route: "report" },
        { id: "GEN-105", name: "Lionsgate World Resort — Intelligence Report (standalone HTML)", type: "report", v: "v2.1", status: "final", date: "Jun 18, 2026", by: "RUN-032 · composer-1", href: "../../exports/Lionsgate Intelligence Report.html" },
      ],
    },
  ];

  const MEMBERS = [
    { name: "V. Gudzenko", email: "vlad@raisable.ai",    tenant: "raisable", role: "Owner",    mfa: true,  active: "today" },
    // GAP — no further members recorded; add real members only (no placeholder personas)
  ];

  // pipeline policy — platform defaults applied to every tenant
  const PIPELINE_POLICY = [
    { stage: "Document parsing",     policy: "Layout-aware OCR · tables & defined terms extracted · originals retained", agent: "parser-1" },
    { stage: "Datapoint extraction", policy: "Confidence floor 40 · every datapoint cites exactly one artifact",          agent: "extractor-1" },
    { stage: "Deep research",        policy: "Web + EDGAR + OpenCorporates + sanctions lists · sources logged",           agent: "research-1 · research-2" },
    { stage: "Fact verification",    policy: "Two-source rule for class V · disagreements auto-registered",               agent: "verifier-1" },
    { stage: "Report composition",   policy: "Generated from the Knowledge Base only — never free-written",               agent: "composer-1" },
    { stage: "Publish gate",         policy: "Human review & sign-off required before any document publishes",            agent: "policy · all tenants" },
  ];

  // ── artifact rows for a project (live project reads the KB sources) ─
  function artifactsFor(proj) {
    if (!proj.live || !R) return proj.artifacts || [];
    const facts = (id) => R.KB.filter((f) => f.source === id).length;
    const rows = Object.entries(R.SRC).map(([id, s]) => {
      const m = (s.file || "").match(/\.(\w+)$/);
      return { id, name: s.name, kind: s.kind === "doc" ? (m ? m[1] : "md") : "platform", file: s.file, status: "parsed", dp: facts(id), uploaded: s.uploaded, parsed: s.parsed };
    });
    return rows.concat(proj.extraArtifacts || []);
  }

  // attach display stats
  PROJECTS.forEach((p) => {
    const arts = artifactsFor(p);
    const steps = Object.values(p.run.steps);
    p.stats = {
      artifacts: arts.length,
      datapoints: p.live && R ? R.KB.length : arts.reduce((a, r) => a + (r.dp || 0), 0),
      docs: p.docs.length,
      stepsDone: steps.filter((s) => s === "done").length,
      stepsTotal: steps.length,
    };
  });

  window.INTEL = {
    TENANTS, PROJECTS, STAGES, STEP_STATUS, MEMBERS, PIPELINE_POLICY, artifactsFor,
    projectsFor: (tid) => PROJECTS.filter((p) => p.tenant === tid),
  };
})();
