import assert from "node:assert/strict";
import {
  installResolveHooks,
  toDataModuleUrl,
} from "./helpers/register-hooks-compat.mjs";

const extensionsShimSource = [
  "export const extension_settings = {};",
  "export function getContext() {",
  "  return {",
  "    chat: [],",
  "    chatMetadata: {},",
  "    extensionSettings: {},",
  "    powerUserSettings: {},",
  "    characters: {},",
  "    characterId: null,",
  "    name1: '',",
  "    name2: '',",
  "    chatId: 'test-chat',",
  "  };",
  "}",
].join("\n");

const scriptShimSource = [
  "export function substituteParamsExtended(value) {",
  "  return String(value ?? '');",
  "}",
].join("\n");

installResolveHooks([
  {
    specifiers: [
      "../../../extensions.js",
      "../../../../extensions.js",
      "../../../../../extensions.js",
    ],
    url: toDataModuleUrl(extensionsShimSource),
  },
  {
    specifiers: [
      "../../../../script.js",
      "../../../../../script.js",
    ],
    url: toDataModuleUrl(scriptShimSource),
  },
]);

const { buildTaskLlmPayload, buildTaskPrompt } = await import("../prompting/prompt-builder.js");
const { createDefaultTaskProfiles } = await import("../prompting/prompt-profiles.js");
const { initializeHostAdapter } = await import("../host/adapter/index.js");

initializeHostAdapter({});

const settings = {
  taskProfilesVersion: 3,
  taskProfiles: createDefaultTaskProfiles(),
};
const extractProfile = settings.taskProfiles.extract.profiles[0];
extractProfile.regex = {
  ...(extractProfile.regex || {}),
  enabled: true,
  inheritStRegex: false,
  sources: {
    global: false,
    preset: false,
    character: false,
  },
  stages: {
    ...(extractProfile.regex?.stages || {}),
    input: true,
    "input.recentMessages": true,
    "input.finalPrompt": false,
  },
  localRules: [
    {
      id: "assistant-local-role-aware",
      script_name: "assistant-local-role-aware",
      enabled: true,
      find_regex: "/继续说明/g",
      replace_string: "助手已净化",
      source: {
        user_input: false,
        ai_output: true,
      },
      destination: {
        prompt: true,
        display: false,
      },
    },
    {
      id: "user-local-role-aware",
      script_name: "user-local-role-aware",
      enabled: true,
      find_regex: "/用户输入/g",
      replace_string: "用户已净化",
      source: {
        user_input: true,
        ai_output: false,
      },
      destination: {
        prompt: true,
        display: false,
      },
    },
  ],
};

const promptBuild = await buildTaskPrompt(settings, "extract", {
  taskName: "extract",
  charDescription: "",
  userPersona: "",
  recentMessages: "这里会被 chatMessages 回填",
  chatMessages: [
    {
      seq: 41,
      role: "assistant",
      content: "继续说明",
      name: "艾琳",
      speaker: "艾琳",
      hideSpeakerLabel: true,
      isContextOnly: true,
    },
    {
      seq: 42,
      role: "user",
      content: "用户输入",
      name: "玩家",
      speaker: "玩家",
      isContextOnly: false,
    },
  ],
  graphStats: "node_count=1",
  schema: "event(title, summary)",
  currentRange: "41 ~ 42",
});
const payload = buildTaskLlmPayload(promptBuild, "fallback-user");
const recentMessages = payload.promptMessages.filter(
  (message) => message.sourceKey === "recentMessages",
);
assert.deepEqual(
  recentMessages.map((message) => ({
    role: message.role,
    sourceKey: message.sourceKey,
    transcriptSection: message.transcriptSection,
    transcriptSectionPart: message.transcriptSectionPart,
  })),
  [
    {
      role: "system",
      sourceKey: "recentMessages",
      transcriptSection: "context",
      transcriptSectionPart: "section",
    },
    {
      role: "system",
      sourceKey: "recentMessages",
      transcriptSection: "target",
      transcriptSectionPart: "section",
    },
  ],
);
assert.match(String(recentMessages[0]?.content || ""), /^--- 以下是上下文回顾（已提取过），仅供理解剧情 ---/);
assert.match(String(recentMessages[0]?.content || ""), /#41 \[assistant\]: 助手已净化/);
assert.match(String(recentMessages[1]?.content || ""), /^--- 以下是本次需要提取记忆的新对话内容 ---/);
assert.match(String(recentMessages[1]?.content || ""), /#42 \[user\|玩家\]: 用户已净化/);
assert.doesNotMatch(
  String(recentMessages[0]?.content || ""),
  /#41 \[assistant\|艾琳\]:/,
);
assert.doesNotMatch(
  String(recentMessages[1]?.content || ""),
  /#42 \[user\|玩家\]: 助手已净化/,
);

console.log("prompt-builder-mixed-transcript tests passed");
