#!/usr/bin/env node
/**
 * 生成桌面端内置的 Next standalone 产物到 `desktop-electron/desktop-next`。
 *
 * 目标：
 * - 打包时不依赖用户机器上的 pnpm / node 环境即可运行（Electron 自身携带 Node）。
 * - 运行期文件读写落到安装目录的 data/（由 Electron 注入 MNOTE_DATA_DIR）。
 *
 * 注意：需要 wolai-frontend 的 next.config.ts 开启 output: "standalone"。
 */

const { spawnSync } = require("child_process");
const fs = require("fs");
const path = require("path");

const rootDir = path.resolve(__dirname, "..");
const frontendDir = path.join(rootDir, "wolai-frontend");
const outDir = path.join(rootDir, "desktop-electron", "desktop-next");

function parseDotenv(filePath) {
  if (!fs.existsSync(filePath)) return {};
  const raw = fs.readFileSync(filePath, { encoding: "utf8" });
  const out = {};
  for (const line of raw.split(/\r?\n/)) {
    const trimmed = line.trim();
    if (!trimmed || trimmed.startsWith("#")) continue;
    const idx = trimmed.indexOf("=");
    if (idx === -1) continue;
    const key = trimmed.slice(0, idx).trim();
    const value = trimmed.slice(idx + 1).trim();
    if (!key) continue;
    out[key] = value;
  }
  return out;
}

function ensureDir(dir) {
  fs.mkdirSync(dir, { recursive: true });
}

function rmDir(dir) {
  fs.rmSync(dir, { recursive: true, force: true });
}

function run(command, cwd, env) {
  const r = spawnSync(command, {
    cwd,
    env: { ...process.env, ...env },
    stdio: "inherit",
    shell: true,
  });
  if (r.status !== 0) {
    process.exit(r.status ?? 1);
  }
}

function assertExists(filePath, hint) {
  if (!fs.existsSync(filePath)) {
    console.error(`\n[prepare-desktop-next] 缺少：${filePath}`);
    if (hint) console.error(`[prepare-desktop-next] 提示：${hint}`);
    process.exit(1);
  }
}

function copyDir(from, to) {
  // 关键：Next standalone 在 pnpm 环境下可能包含大量 symlink/junction。
  // electron-builder 在复制 extraResources 时对链接目录处理不稳定，
  // 因此这里强制“解引用复制”，把真实文件复制出来，确保运行期能 require('next')。
  fs.cpSync(from, to, { recursive: true, force: true, dereference: true });
}

function main() {
  console.log("[prepare-desktop-next] 开始构建 wolai-frontend（standalone）…");

  // 约定：全局仅使用仓库根目录的 .env.all 作为配置来源（生产优先）。
  // 桌面端如需覆盖，可通过系统环境变量注入（例如在启动命令前临时设置）。
  const envAllPath = path.join(rootDir, ".env.all");
  assertExists(envAllPath, "请先在仓库根目录创建 .env.all（全局唯一 env 文件）。");
  const desktopEnv = {
    ...parseDotenv(envAllPath),
  };
  console.log("[prepare-desktop-next] 桌面端 env 摘要：", {
    NEXT_PUBLIC_BACKEND_URL: desktopEnv.NEXT_PUBLIC_BACKEND_URL,
    NEXT_PUBLIC_ONLYOFFICE_BASE_URL: desktopEnv.NEXT_PUBLIC_ONLYOFFICE_BASE_URL,
  });

  run("pnpm -C wolai-frontend build", rootDir, {
    NODE_ENV: "production",
    NEXT_TELEMETRY_DISABLED: "1",
    ...desktopEnv,
  });

  const standaloneDir = path.join(frontendDir, ".next", "standalone");
  const staticDir = path.join(frontendDir, ".next", "static");
  const publicDir = path.join(frontendDir, "public");

  assertExists(
    path.join(standaloneDir, "server.js"),
    '请在 wolai-frontend/next.config.ts 增加 `output: "standalone"` 后重试。',
  );
  assertExists(staticDir, "Next build 未生成 .next/static（可能构建失败或目录异常）。");
  assertExists(publicDir, "wolai-frontend/public 不存在。");

  console.log(`[prepare-desktop-next] 清理旧产物：${outDir}`);
  rmDir(outDir);
  ensureDir(outDir);

  console.log("[prepare-desktop-next] 复制 standalone …");
  copyDir(standaloneDir, outDir);

  console.log("[prepare-desktop-next] 补齐 .next/static …");
  ensureDir(path.join(outDir, ".next"));
  copyDir(staticDir, path.join(outDir, ".next", "static"));

  console.log("[prepare-desktop-next] 补齐 public …");
  copyDir(publicDir, path.join(outDir, "public"));

  console.log("[prepare-desktop-next] 完成。");
}

main();
