package com.common.util;



import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.common.entity.SyslogNormalData;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Component;

import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.util.ArrayList;
import java.util.List;
import java.util.UUID;

@Slf4j
@Component
public class AlgorithmResultParser {

    private static final DateTimeFormatter[] DATE_FORMATTERS = {
            DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss"),
            DateTimeFormatter.ofPattern("yyyy/MM/dd HH:mm:ss"),
            DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss.SSS"),
            DateTimeFormatter.ofPattern("yyyy-MM-dd'T'HH:mm:ss"),
            DateTimeFormatter.ofPattern("yyyy-MM-dd'T'HH:mm:ss.SSS")
    };

    /**
     * 构建示例JSON对应的newLogs
     */
    public List<SyslogNormalData> buildNewLogsFromExample() {
        String exampleJson = "[\n" +
                "    {\n" +
                "        \"_index\": \"es:skyeye-weblog-2025.09.30\",\n" +
                "        \"access_time\": \"2025-09-30 12:05:00\",\n" +
                "        \"dip\": \"10.20.30.51\",\n" +
                "        \"dname\": \"网页木马流量\",\n" +
                "        \"dtype\": \"疑似木马活动\",\n" +
                "        \"host\": \"\",\n" +
                "        \"log_id\": \"hidden-002\",\n" +
                "        \"origin_field\": \"匹配到文件名: shell.php:.jpg 与 匹配到恶意请求: exec=dir\",\n" +
                "        \"reason\": \"源IP 203.0.113.51 访问 目的IP 10.20.30.51 异常，入度=0, 出度=0, 独立访客=1，匹配到文件名: shell.php:.jpg，匹配到恶意请求: exec=dir\",\n" +
                "        \"referer\": \"\",\n" +
                "        \"sip\": \"203.0.113.51\",\n" +
                "        \"status_code\": 200,\n" +
                "        \"url\": \"/admin/shell.php:.jpg\"\n" +
                "    }\n" +
                "]";

        return parseJsonToLogs(exampleJson);
    }

    /**
     * 解析JSON字符串为SyslogNormalData列表
     */
    public List<SyslogNormalData> parseJsonToLogs(String jsonStr) {
        List<SyslogNormalData> logs = new ArrayList<>();

        try {
            JSONArray jsonArray = JSON.parseArray(jsonStr);

            for (int i = 0; i < jsonArray.size(); i++) {
                JSONObject jsonObj = jsonArray.getJSONObject(i);
                SyslogNormalData logData = convertJsonObject(jsonObj);
                if (logData != null) {
                    logs.add(logData);
                }
            }

            log.info("成功解析 {} 条日志数据", logs.size());

        } catch (Exception e) {
            log.error("解析JSON失败: {}", e.getMessage(), e);
        }

        return logs;
    }

    /**
     * 转换单个JSON对象
     */
    private SyslogNormalData convertJsonObject(JSONObject jsonObj) {
        try {
            SyslogNormalData logData = new SyslogNormalData();

            // 基础字段
            logData.setId(getString(jsonObj, "log_id", UUID.randomUUID().toString()));
            logData.setSyslogUuid(UUID.randomUUID().toString());
            logData.setLogId(getString(jsonObj, "log_id"));

            // 时间字段
            LocalDateTime now = LocalDateTime.now();
            logData.setCreatedAt(now);
            logData.setEventDate(now);

            String accessTime = getString(jsonObj, "access_time");
            if (accessTime != null && !accessTime.isEmpty()) {
                LocalDateTime logTime = parseDateTime(accessTime);
                logData.setLogTime(logTime != null ? logTime : now);
            } else {
                logData.setLogTime(now);
            }

            // IP字段
            logData.setSrcIp(getString(jsonObj, "sip"));
            logData.setDestIp(getString(jsonObj, "dip"));
            logData.setSrcIpStr(getString(jsonObj, "sip"));
            logData.setDestIpStr(getString(jsonObj, "dip"));

            // HTTP字段
            logData.setHttpUrl(getString(jsonObj, "url"));
            logData.setHttpHost(getString(jsonObj, "host"));
            logData.setHttpReferer(getString(jsonObj, "referer"));
            logData.setHttpStatusCode(getLong(jsonObj, "status_code", 200L));
            logData.setHttpMethod("GET");

            // 安全检测字段
            logData.setAttackResult(1);
            logData.setEventCategory(1);
            logData.setEventType(1);
            logData.setEventLevel(3);
            logData.setEngineType(getString(jsonObj, "dtype"));
            logData.setOriginRuleName(getString(jsonObj, "dname"));
            logData.setOriginEventName(getString(jsonObj, "dname"));
            logData.setDescription(getString(jsonObj, "reason"));
            logData.setOriginAttackResult(getString(jsonObj, "origin_field"));

            // 协议
            logData.setProto("http");
            logData.setSyslogTopic("algorithm_detection");

            // 从origin_field提取额外信息
            String originField = getString(jsonObj, "origin_field");
            if (originField != null) {
                extractAdditionalInfo(logData, originField);
            }

            // 设置索引信息
            logData.setId(getString(jsonObj, "_index"));

            return logData;

        } catch (Exception e) {
            log.error("转换JSON对象失败: {}", e.getMessage());
            return null;
        }
    }

    /**
     * 从origin_field提取额外信息
     */
    private void extractAdditionalInfo(SyslogNormalData logData, String originField) {
        // 提取文件名
        if (originField.contains("文件名:")) {
            String[] parts = originField.split("文件名:");
            if (parts.length > 1) {
                String fileInfo = parts[1].split("与")[0].trim();
                logData.setFileName(fileInfo);
                logData.setFileType(determineFileType(fileInfo));

                if (fileInfo.toLowerCase().contains("shell")) {
                    logData.setWebshellType("疑似Webshell");
                    logData.setBackdoorType("网页后门");
                }
            }
        }

        // 提取恶意请求
        if (originField.contains("恶意请求:")) {
            String[] parts = originField.split("恶意请求:");
            if (parts.length > 1) {
                String maliciousRequest = parts[1].trim();
                logData.setCmdline(maliciousRequest);
                logData.setShellCmdline(maliciousRequest);
                logData.setDetail(maliciousRequest);

                // 检查是否是命令执行
                if (maliciousRequest.contains("exec=") ||
                        maliciousRequest.contains("cmd=") ||
                        maliciousRequest.contains("system(")) {
                    logData.setOriginAttackAction("命令执行");
                }
            }
        }
    }

    /**
     * 根据文件名确定文件类型
     */
    private String determineFileType(String fileName) {
        if (fileName == null) return "";

        fileName = fileName.toLowerCase();

        if (fileName.endsWith(".php") || fileName.contains(".php:")) {
            return "php";
        } else if (fileName.endsWith(".jsp")) {
            return "jsp";
        } else if (fileName.endsWith(".asp") || fileName.endsWith(".aspx")) {
            return "asp";
        } else if (fileName.endsWith(".jpg") || fileName.endsWith(".jpeg")) {
            return "image";
        } else if (fileName.endsWith(".png")) {
            return "image";
        } else if (fileName.endsWith(".gif")) {
            return "image";
        } else if (fileName.endsWith(".bmp")) {
            return "image";
        } else if (fileName.endsWith(".exe")) {
            return "executable";
        } else if (fileName.endsWith(".dll")) {
            return "library";
        } else if (fileName.endsWith(".bat") || fileName.endsWith(".cmd")) {
            return "batch";
        } else if (fileName.endsWith(".sh")) {
            return "shell";
        } else if (fileName.endsWith(".py")) {
            return "python";
        } else if (fileName.endsWith(".js")) {
            return "javascript";
        } else if (fileName.endsWith(".html") || fileName.endsWith(".htm")) {
            return "html";
        } else if (fileName.endsWith(".css")) {
            return "css";
        } else if (fileName.endsWith(".xml")) {
            return "xml";
        } else if (fileName.endsWith(".json")) {
            return "json";
        } else if (fileName.endsWith(".txt")) {
            return "text";
        } else if (fileName.endsWith(".pdf")) {
            return "pdf";
        } else if (fileName.endsWith(".doc") || fileName.endsWith(".docx")) {
            return "document";
        } else if (fileName.endsWith(".xls") || fileName.endsWith(".xlsx")) {
            return "spreadsheet";
        } else if (fileName.endsWith(".zip") || fileName.endsWith(".rar") ||
                fileName.endsWith(".7z") || fileName.endsWith(".tar") ||
                fileName.endsWith(".gz")) {
            return "archive";
        } else {
            return "unknown";
        }
    }

    /**
     * 解析时间字符串
     */
    private LocalDateTime parseDateTime(String timeStr) {
        if (timeStr == null || timeStr.isEmpty()) {
            return LocalDateTime.now();
        }

        for (DateTimeFormatter formatter : DATE_FORMATTERS) {
            try {
                return LocalDateTime.parse(timeStr, formatter);
            } catch (Exception e) {
                // 继续尝试下一个格式
            }
        }

        // 如果所有格式都失败，尝试其他格式
        try {
            // 尝试处理带有时区的时间格式
            if (timeStr.contains("T")) {
                return LocalDateTime.parse(timeStr,
                        DateTimeFormatter.ISO_LOCAL_DATE_TIME);
            }

            // 尝试处理日期部分
            if (timeStr.length() >= 10) {
                String datePart = timeStr.substring(0, 10);
                return LocalDateTime.parse(datePart + "T00:00:00");
            }
        } catch (Exception e) {
            log.warn("无法解析时间字符串: {}, 使用当前时间", timeStr);
        }

        return LocalDateTime.now();
    }

    /**
     * 安全获取字符串字段
     */
    private String getString(JSONObject jsonObj, String key) {
        return getString(jsonObj, key, "");
    }

    private String getString(JSONObject jsonObj, String key, String defaultValue) {
        try {
            String value = jsonObj.getString(key);
            return value != null ? value : defaultValue;
        } catch (Exception e) {
            return defaultValue;
        }
    }

    /**
     * 安全获取Long字段
     */
    private Long getLong(JSONObject jsonObj, String key, Long defaultValue) {
        try {
            Long value = jsonObj.getLong(key);
            return value != null ? value : defaultValue;
        } catch (Exception e) {
            return defaultValue;
        }
    }

    /**
     * 安全获取Integer字段
     */
    private Integer getInteger(JSONObject jsonObj, String key, Integer defaultValue) {
        try {
            Integer value = jsonObj.getInteger(key);
            return value != null ? value : defaultValue;
        } catch (Exception e) {
            return defaultValue;
        }
    }
}