import { test } from "node:test";
import assert from "node:assert/strict";
import { DatabaseSync } from "node:sqlite";
import {
  workAgentHeartbeat,
  workAgentRegister,
  workContextGet,
  workContextList,
  workContextUpsert,
  workDecisionApprove,
  workDecisionPropose,
  workEvidenceAttach,
  workItemCreate,
  workItemList,
  workItemUpdate,
  workMemoryApprove,
  workMemoryPropose,
  workMessageCreate,
  workMessageList,
  workModuleSnapshot,
  workSessionHeartbeat,
  workSessionRegister,
} from "./work.ts";

test("work core records a GTM context, session, agent, item, evidence, memory, and decision", () => {
  const db = new DatabaseSync(":memory:");

  const context = workContextUpsert(db, {
    module: "GTM",
    slug: "agency-founder-outbound",
    kind: "campaign",
    title: "Agency founder outbound",
    subtitle: "36 strict ICP leads",
    metadata: { client: "Dewx" },
  }) as any;
  assert.equal(context.module, "gtm");
  assert.equal(context.slug, "agency-founder-outbound");

  const session = workSessionRegister(db, {
    module: "gtm",
    context_slug: "agency-founder-outbound",
    purpose: "research strict ICP evidence",
    owner: "researcher",
    tool: "codex-server",
    status: "running",
    metadata: { host: "server" },
  }) as any;
  assert.equal(session.context_id, context.id);
  assert.equal(session.status, "running");
  assert.equal(workSessionHeartbeat(db, { session_id: session.id, status: "live" }).ok, true);

  const agent = workAgentRegister(db, {
    module: "gtm",
    context_slug: "agency-founder-outbound",
    name: "Researcher",
    tool: "codex-server",
    status: "running",
    current_task: "check source evidence",
    session_id: session.id,
  }) as any;
  assert.equal(agent.context_id, context.id);
  assert.equal(workAgentHeartbeat(db, { agent_id: agent.id, status: "live" }).ok, true);

  const item = workItemCreate(db, {
    module: "gtm",
    context_slug: "agency-founder-outbound",
    kind: "reply",
    title: "Draft reply for high-signal lead",
    priority: "high",
    session_id: session.id,
  }) as any;
  assert.equal(item.status, "open");
  assert.equal((workItemList(db, { module: "gtm", status: "open" }) as any[]).length, 1);
  const updated = workItemUpdate(db, { item_id: item.id, status: "blocked", summary: "Needs source evidence" }) as any;
  assert.equal(updated.ok, true);
  assert.equal(updated.item.status, "blocked");

  const evidence = workEvidenceAttach(db, {
    module: "gtm",
    context_slug: "agency-founder-outbound",
    item_id: item.id,
    session_id: session.id,
    kind: "browser",
    title: "Company research snapshot",
    uri: "file:///tmp/research.json",
  }) as any;
  assert.equal(evidence.item_id, item.id);

  const message = workMessageCreate(db, {
    module: "gtm",
    context_slug: "agency-founder-outbound",
    session_id: session.id,
    agent_id: agent.id,
    speaker: "Researcher",
    role: "agent",
    body: "I found the source evidence and attached it to the reply item.",
  }) as any;
  assert.equal(message.context_id, context.id);
  assert.equal(message.speaker, "Researcher");
  assert.equal((workMessageList(db, { module: "gtm", context_slug: "agency-founder-outbound" }) as any[]).length, 1);

  const memory = workMemoryPropose(db, {
    module: "gtm",
    context_slug: "agency-founder-outbound",
    kind: "fact",
    body: "Only use strict ICP evidence before drafting.",
    source: evidence.id,
  }) as any;
  assert.equal(memory.status, "proposed");
  assert.deepEqual(workMemoryApprove(db, { memory_id: memory.id, owner: "Roki" }), { ok: true, status: "approved" });

  const decision = workDecisionPropose(db, {
    module: "gtm",
    context_slug: "agency-founder-outbound",
    title: "Hold sends behind approval",
    proposal: "Create drafts only; external sends require explicit approval.",
    risk: "external",
  }) as any;
  assert.equal(decision.status, "proposed");
  assert.deepEqual(workDecisionApprove(db, { decision_id: decision.id, decided_by: "Roki" }), { ok: true, status: "approved" });

  const deep = workContextGet(db, { module: "gtm", context_slug: "agency-founder-outbound" }) as any;
  assert.equal(deep.recent_items.length, 1);
  assert.equal(deep.sessions.length, 1);
  assert.equal(deep.agents.length, 1);
  assert.equal(deep.evidence.length, 1);
  assert.equal(deep.decisions.length, 1);
  assert.equal(deep.memory.length, 1);
  assert.equal(deep.messages.length, 1);

  const listed = workContextList(db, { module: "gtm" }) as any[];
  assert.equal(listed[0].open_items, 1);
  assert.equal(listed[0].live_agents, 1);

  const snapshot = workModuleSnapshot(db, { module: "gtm" }) as any;
  assert.equal(snapshot.contexts.length, 1);
  assert.equal(snapshot.items.length, 0); // snapshot only includes open items; this one is blocked
  assert.equal(snapshot.messages.length, 1);
});
