import { randomBytes } from "node:crypto";
import { existsSync, mkdirSync, readFileSync, writeFileSync } from "node:fs";
import os from "node:os";
import path from "node:path";
import { stdin as input, stdout as output } from "node:process";
import { createInterface } from "node:readline/promises";
import { logger } from "../utils/logger.js";
import { getAutoRegisterConfigFilePath } from "./auto-register.js";
function normalizeAnswer(answer) {
    return answer.trim().toLowerCase();
}
function isYes(answer) {
    return ["", "y", "yes", "是", "好", "配置"].includes(normalizeAnswer(answer));
}
function isNo(answer) {
    return ["n", "no", "否", "不", "跳过", "skip", "s"].includes(normalizeAnswer(answer));
}
function writeConfigFile(configPath, config) {
    mkdirSync(path.dirname(configPath), { recursive: true });
    writeFileSync(configPath, `${JSON.stringify(config, null, 2)}\n`, "utf-8");
}
function readExistingConfig(configPath) {
    if (!existsSync(configPath)) {
        return {};
    }
    try {
        const parsed = JSON.parse(readFileSync(configPath, "utf-8"));
        return parsed && typeof parsed === "object" && !Array.isArray(parsed)
            ? parsed
            : {};
    }
    catch (error) {
        const err = error;
        logger.warn(`[runtime-bridge] 读取现有配置失败，将使用空默认值: ${err.message}`);
        return {};
    }
}
function generateDefaultConnectionKey() {
    return `awsb_${randomBytes(24).toString("base64url")}`;
}
function writeSkippedConfig(configPath, generateConnectionKey) {
    const connectionKey = generateConnectionKey();
    writeConfigFile(configPath, { connectionKey });
    const message = `[runtime-bridge] 已创建配置文件: ${configPath}\n` +
        `[runtime-bridge] 自动生成 connectionKey: ${connectionKey}\n` +
        "[runtime-bridge] 请保存该 connectionKey；server/面板连接此 Bridge 时需要使用它。";
    logger.info(message);
    output.write(`${message}\n`);
}
async function askOptional(prompt, label, defaultValue) {
    const answer = await prompt.question(`${label}（默认使用当前值 ${defaultValue}，直接回车保留）: `);
    return answer.trim() || defaultValue;
}
async function askRequired(prompt, label, currentValue) {
    for (;;) {
        const answer = (await prompt.question(currentValue
            ? `${label}（默认使用当前值 ${currentValue}，直接回车保留）: `
            : `${label}: `)).trim();
        if (answer) {
            return answer;
        }
        if (currentValue) {
            return currentValue;
        }
        output.write(`${label} 不能为空，请重新输入。\n`);
    }
}
async function askShouldConfigure(prompt) {
    for (;;) {
        const answer = await prompt.question("未检测到 ~/.aws-bridge/config.json，是否现在进入自动注册配置引导？(Y/n): ");
        if (isYes(answer)) {
            return true;
        }
        if (isNo(answer)) {
            return false;
        }
        output.write("请输入 Y 继续配置，或输入 n 跳过。\n");
    }
}
async function collectStartupConfig(prompt, existingConfig = {}) {
    const existingTarget = existingConfig.autoRegisterTargets?.[0] || {};
    const defaultServerUrl = "http://127.0.0.1:8080";
    const defaultInstanceName = os.hostname() || "AgentsWork Runtime Bridge";
    const defaultRegisterIp = "127.0.0.1";
    const connectionKey = await askRequired(prompt, "connectionKey（面板连接 Bridge 的密钥）", existingConfig.connectionKey);
    const serverUrl = await askOptional(prompt, "serverUrl（调度中心地址）", existingTarget.serverUrl || defaultServerUrl);
    const instanceName = await askOptional(prompt, "instanceName（实例名称）", existingTarget.instanceName || defaultInstanceName);
    const userKey = await askRequired(prompt, "userKey（用户 API Key）", existingTarget.userKey);
    const registerIp = await askOptional(prompt, "registerIp（Bridge 对外访问 IP）", existingTarget.registerIp || defaultRegisterIp);
    return {
        ...existingConfig,
        connectionKey,
        autoRegisterTargets: [
            {
                ...existingTarget,
                serverUrl,
                instanceName,
                userKey,
                registerIp,
            },
        ],
    };
}
async function createPrompt(options) {
    return {
        prompt: options.prompt || createInterface({ input, output, terminal: true }),
        shouldClosePrompt: !options.prompt,
    };
}
export async function ensureStartupConfig(options = {}) {
    const configPath = options.configPath || getAutoRegisterConfigFilePath();
    const generateConnectionKey = options.generateConnectionKey || generateDefaultConnectionKey;
    if (existsSync(configPath)) {
        return "exists";
    }
    const env = options.env || process.env;
    if (env.AWS_BRIDGE_SKIP_SETUP === "true") {
        writeSkippedConfig(configPath, generateConnectionKey);
        logger.info("[runtime-bridge] AWS_BRIDGE_SKIP_SETUP=true，跳过首次配置引导");
        return "skipped";
    }
    const interactive = options.interactive ?? Boolean(process.stdin.isTTY && process.stdout.isTTY);
    if (!interactive) {
        writeSkippedConfig(configPath, generateConnectionKey);
        logger.info(`[runtime-bridge] 未检测到配置文件: ${configPath}；当前为非交互环境，跳过首次配置引导`);
        return "non-interactive";
    }
    const { prompt, shouldClosePrompt } = await createPrompt(options);
    try {
        const shouldConfigure = await askShouldConfigure(prompt);
        if (!shouldConfigure) {
            writeSkippedConfig(configPath, generateConnectionKey);
            logger.info("[runtime-bridge] 已跳过首次配置引导");
            return "skipped";
        }
        const config = await collectStartupConfig(prompt);
        writeConfigFile(configPath, config);
        logger.info(`[runtime-bridge] 已写入配置文件: ${configPath}`);
        return "created";
    }
    catch (error) {
        const err = error;
        logger.warn(`[runtime-bridge] 首次配置引导失败: ${err.message}`);
        return "failed";
    }
    finally {
        if (shouldClosePrompt) {
            prompt.close();
        }
    }
}
export async function configureStartupConfig(options = {}) {
    const configPath = options.configPath || getAutoRegisterConfigFilePath();
    const interactive = options.interactive ?? Boolean(process.stdin.isTTY && process.stdout.isTTY);
    if (!interactive) {
        logger.warn("[runtime-bridge] awsb config 需要交互式终端");
        return "failed";
    }
    const { prompt, shouldClosePrompt } = await createPrompt(options);
    try {
        const existingConfig = readExistingConfig(configPath);
        const config = await collectStartupConfig(prompt, existingConfig);
        writeConfigFile(configPath, config);
        logger.info(`[runtime-bridge] 已更新配置文件: ${configPath}`);
        return "configured";
    }
    catch (error) {
        const err = error;
        logger.warn(`[runtime-bridge] 配置引导失败: ${err.message}`);
        return "failed";
    }
    finally {
        if (shouldClosePrompt) {
            prompt.close();
        }
    }
}
