package com.njcn.gather.icd.mapping.debug;

import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.SerializationFeature;
import com.njcn.gather.icd.mapping.component.IcdToXmlResponseConverter;
import com.njcn.gather.icd.mapping.pojo.bo.IcdToXmlGenerateResult;
import com.njcn.gather.icd.mapping.pojo.enums.GenerateStatus;
import com.njcn.gather.icd.mapping.service.impl.IcdToXmlTaskAppService;
import org.springframework.boot.Banner;
import org.springframework.boot.WebApplicationType;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.builder.SpringApplicationBuilder;
import org.springframework.context.ConfigurableApplicationContext;

import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;

/**
 * JSON 转 XML 本地调试入口。
 *
 * 使用方式：
 * 1. 先通过 GetIcdMmsJsonDebugRunner 获取 mappingJson，或使用已有的 JSON 文件。
 * 2. 修改 MMS_JSON_FILE_PATH 指向包含 mappingJson 的文件路径。
 * 3. 直接运行 main，查看生成的 XML 内容。
 * 4. 可选：设置 SAVE_XML_TO_DISK = true 将 XML 保存到磁盘。
 */
public class JsonToXmlDebugRunner {

    /** 
     * 包含 mappingJson 的文件路径。
     * 文件格式：纯文本，内容为 getIcdMmsJson 接口返回的 mappingJson 字段值。
     * 或者完整的 MappingTaskResponse JSON（会自动提取 mappingJson 字段）。
     */
    private static final String MMS_JSON_FILE_PATH = "D:/temp/mms-output/mapping.json";

    /** 是否输出格式化 XML，便于人工查看。 */
    private static final boolean PRETTY_XML = true;

    /** 是否把生成的 XML 写入磁盘。 */
    private static final boolean SAVE_XML_TO_DISK = true;

    /** saveXmlToDisk=true 时使用的输出文件路径。 */
    private static final String OUTPUT_XML_PATH = "D:/temp/mms-output/generated-config.xml";

    /** 是否打印详细的转换过程日志。 */
    private static final boolean VERBOSE_LOG = true;

    public static void main(String[] args) {
        try (ConfigurableApplicationContext context = new SpringApplicationBuilder(DebugApplication.class)
                .web(WebApplicationType.NONE)
                .bannerMode(Banner.Mode.OFF)
                .logStartupInfo(false)
                .run(args)) {
            
            IcdToXmlTaskAppService icdToXmlTaskAppService = context.getBean(IcdToXmlTaskAppService.class);
            IcdToXmlResponseConverter responseConverter = context.getBean(IcdToXmlResponseConverter.class);
            ObjectMapper objectMapper = createObjectMapper();

            if (VERBOSE_LOG) {
                System.out.println("========== JSON 转 XML 调试开始 ==========");
                System.out.println("输入文件: " + MMS_JSON_FILE_PATH);
                System.out.println("输出文件: " + (SAVE_XML_TO_DISK ? OUTPUT_XML_PATH : "(不保存)"));
                System.out.println();
            }

            // 读取 JSON 文件
            String jsonContent = readJsonFile();
            if (VERBOSE_LOG) {
                System.out.println("✓ JSON 文件读取成功，长度: " + jsonContent.length() + " 字符");
            }

            // 提取 mappingJson（可能是完整响应或纯 mappingJson）
            String mappingJson = extractMappingJson(jsonContent, objectMapper);
            if (VERBOSE_LOG) {
                System.out.println("✓ MappingJSON 提取成功，长度: " + mappingJson.length() + " 字符");
                System.out.println();
            }

            // 调用服务生成 XML
            if (VERBOSE_LOG) {
                System.out.println("正在转换 JSON 为 XML...");
            }
            IcdToXmlGenerateResult result = icdToXmlTaskAppService.generateXmlFromJson(mappingJson,2);

            // 输出结果
            printResult(result, objectMapper);

            // 保存 XML 到磁盘
            if (SAVE_XML_TO_DISK && result.getStatus() == GenerateStatus.SUCCESS) {
                saveXmlToDisk(result.getXmlContent());
            }

            if (VERBOSE_LOG) {
                System.out.println();
                System.out.println("========== JSON 转 XML 调试结束 ==========");
            }

        } catch (Exception ex) {
            throw new IllegalStateException("JSON 转 XML 调试失败：" + ex.getMessage(), ex);
        }
    }

    /**
     * 读取 JSON 文件内容。
     */
    private static String readJsonFile() {
        Path jsonPath = Paths.get(MMS_JSON_FILE_PATH);
        if (!Files.exists(jsonPath)) {
            throw new IllegalArgumentException("JSON 文件不存在：" + jsonPath.toAbsolutePath());
        }

        try {
            byte[] bytes = Files.readAllBytes(jsonPath);
            return new String(bytes, StandardCharsets.UTF_8);
        } catch (Exception ex) {
            throw new IllegalArgumentException("读取 JSON 文件失败：" + ex.getMessage(), ex);
        }
    }

    /**
     * 从 JSON 内容中提取 mappingJson。
     * 支持两种格式：
     * 1. 完整的 MappingTaskResponse JSON（包含 mappingJson 字段）
     * 2. 纯 mappingJson 字符串
     */
    private static String extractMappingJson(String jsonContent, ObjectMapper objectMapper) {
        try {
            if (jsonContent.trim().startsWith("{")) {
                java.util.Map<String, Object> jsonMap = objectMapper.readValue(
                    jsonContent, 
                    java.util.Map.class
                );
                
                if (jsonMap.containsKey("mappingJson")) {
                    Object mappingJsonObj = jsonMap.get("mappingJson");
                    if (mappingJsonObj != null) {
                        if (mappingJsonObj instanceof String) {
                            return (String) mappingJsonObj;
                        } else {
                            return objectMapper.writeValueAsString(mappingJsonObj);
                        }
                    }
                }
            }
            
            // 如果不是对象或不包含 mappingJson，则假设整个内容就是 mappingJson
            return jsonContent;
        } catch (Exception ex) {
            // 如果解析失败，也假设整个内容就是 mappingJson
            return jsonContent;
        }
    }

    /**
     * 打印转换结果。
     */
    private static void printResult(IcdToXmlGenerateResult result, ObjectMapper objectMapper) {
        System.out.println();
        System.out.println("===== 转换结果 =====");
        System.out.println("状态: " + result.getStatus());
        System.out.println("消息: " + result.getMessage());
        
        if (result.getProblems() != null && !result.getProblems().isEmpty()) {
            System.out.println("问题列表:");
            for (String problem : result.getProblems()) {
                System.out.println("  - " + problem);
            }
        }

//        if (result.getStatus() == GenerateStatus.SUCCESS) {
//            System.out.println();
//            System.out.println("----- 生成的 XML 内容 -----");
//            String xmlContent = result.getMappingXml();
//
//            if (PRETTY_XML) {
//                // 简单格式化：每个标签独占一行
//                xmlContent = formatXml(xmlContent);
//            }
//
//            System.out.println(xmlContent);
//            System.out.println("--------------------------");
//            System.out.println();
//            System.out.println("XML 长度: " + result.getMappingXml().length() + " 字符");
//        }
    }

    /**
     * 简单的 XML 格式化。
     */
    private static String formatXml(String xml) {
        if (xml == null || xml.isEmpty()) {
            return xml;
        }

        // 在标签前后添加换行
        String formatted = xml.replaceAll(">", ">\n")
                              .replaceAll("<", "\n<")
                              .replaceAll("\n\n", "\n");

        // 简单的缩进处理
        StringBuilder result = new StringBuilder();
        int indentLevel = 0;
        String[] lines = formatted.split("\n");
        
        for (String line : lines) {
            line = line.trim();
            if (line.isEmpty()) {
                continue;
            }

            // 如果是闭合标签，减少缩进
            if (line.startsWith("</") && !line.endsWith("/>")) {
                indentLevel = Math.max(0, indentLevel - 1);
            }

            // 添加缩进
            for (int i = 0; i < indentLevel; i++) {
                result.append("  ");
            }
            result.append(line).append("\n");

            // 如果是开始标签且不是自闭合，增加缩进
            if (line.startsWith("<") && !line.startsWith("</") 
                && !line.endsWith("/>") && !line.endsWith(">")) {
                indentLevel++;
            }
        }

        return result.toString();
    }

    /**
     * 保存 XML 到磁盘。
     */
    private static void saveXmlToDisk(String xmlContent) {
        try {
            Path outputPath = Paths.get(OUTPUT_XML_PATH);
            
            // 创建父目录
            if (outputPath.getParent() != null && !Files.exists(outputPath.getParent())) {
                Files.createDirectories(outputPath.getParent());
            }

            Files.write(outputPath, xmlContent.getBytes(StandardCharsets.UTF_8));
            
            System.out.println("✓ XML 已保存到: " + outputPath.toAbsolutePath());
            System.out.println("  文件大小: " + Files.size(outputPath) + " 字节");
        } catch (Exception ex) {
            throw new IllegalStateException("保存 XML 文件失败：" + ex.getMessage(), ex);
        }
    }

    private static ObjectMapper createObjectMapper() {
        ObjectMapper objectMapper = new ObjectMapper();
        objectMapper.enable(SerializationFeature.INDENT_OUTPUT);
        return objectMapper;
    }

    @SpringBootApplication(scanBasePackages = "com.njcn.gather.icd.mapping")
    public static class DebugApplication {
    }
}
