package services

import (
	"bytes"
	"ems-backend/models"
	"encoding/json"
	"errors"
	"fmt"
	"io"
	"log"
	"net/http"
	"strings"
	"time"

	"github.com/google/uuid"
)

// CheckAndAutoHandleAlarms 检查告警数量并执行自动处理
func CheckAndAutoHandleAlarms() {
	// 1. 获取配置
	var autoAck, thresholdStr string
	models.DB.Model(&models.SysConfig{}).Where("config_key = ?", "ai_auto_ack").Select("config_value").Scan(&autoAck)
	models.DB.Model(&models.SysConfig{}).Where("config_key = ?", "ai_alert_threshold").Select("config_value").Scan(&thresholdStr)

	if autoAck != "true" {
		return
	}

	threshold := 200 // 默认值
	if _, err := fmt.Sscanf(thresholdStr, "%d", &threshold); err != nil {
		// 解析失败使用默认值
	}

	// 2. 检查当前活跃告警数量
	var count int64
	models.DB.Model(&models.AlarmLog{}).Where("status = ?", "ACTIVE").Count(&count)

	if count > int64(threshold) {
		log.Printf("Active alarms (%d) exceeded threshold (%d), triggering auto-confirm...", count, threshold)
		go processAutoConfirmAndReport()
	}
}

func processAutoConfirmAndReport() {
	// 1. 获取待确认的300条告警
	var alarms []models.AlarmLog
	err := models.DB.Where("status = ?", "ACTIVE").
		Order("start_time asc"). // 处理最早的告警
		Limit(300).
		Find(&alarms).Error

	if err != nil || len(alarms) == 0 {
		return
	}

	// 2. 批量确认告警 (更新状态为 CONFIRMED)
	var alarmIDs []uuid.UUID
	for _, a := range alarms {
		alarmIDs = append(alarmIDs, a.ID)
	}

	tx := models.DB.Begin()
	// 注意：AlarmLog 的状态字段可能是 Status 或 status，根据 schema.go 是 Status
	if err := tx.Model(&models.AlarmLog{}).
		Where("id IN ?", alarmIDs).
		Update("status", "CONFIRMED").Error; err != nil {
		tx.Rollback()
		log.Printf("Failed to auto-confirm alarms: %v", err)
		return
	}
	tx.Commit()

	// 3. 生成 AI 分析报表
	GenerateAIReportInternal(alarms, fmt.Sprintf("自动告警处理报告 (已确认 %d 条) - %s", len(alarms), time.Now().Format("2006-01-02 15:04:05")), "AUTO_ALARM_ANALYSIS")
}

// GenerateAIReportInternal 内部生成报表逻辑
func GenerateAIReportInternal(alarms []models.AlarmLog, title string, reportType string) (*models.AIAnalysisReport, error) {
	// 获取 AI 配置
	var apiUrl, apiKey, model string
	models.DB.Model(&models.SysConfig{}).Where("config_key = ?", "ai_api_url").Select("config_value").Scan(&apiUrl)
	models.DB.Model(&models.SysConfig{}).Where("config_key = ?", "ai_api_key").Select("config_value").Scan(&apiKey)
	models.DB.Model(&models.SysConfig{}).Where("config_key = ?", "ai_model").Select("config_value").Scan(&model)

	if apiUrl == "" || apiKey == "" {
		return nil, errors.New("AI configuration missing")
	}
	if model == "" {
		model = "gpt-3.5-turbo"
	}

	// 创建报表记录
	report := models.AIAnalysisReport{
		ReportType: reportType,
		Title:      title,
		Status:     "GENERATING",
		AlertCount: len(alarms),
	}
	if err := models.DB.Create(&report).Error; err != nil {
		return nil, err
	}

	// 异步调用 AI
	go func(rID uuid.UUID, alarms []models.AlarmLog, url, key, model string) {
		// 构建 Prompt
		prompt := fmt.Sprintf("系统包含 %d 条告警信息。以下是这些告警的摘要（前20条）：\n", len(alarms))
		limit := 20
		if len(alarms) < 20 {
			limit = len(alarms)
		}
		for i := 0; i < limit; i++ {
			a := alarms[i]
			prompt += fmt.Sprintf("- [%s] 类型: %s, 内容: %s\n", a.StartTime.Format("15:04:05"), a.Type, a.Content)
		}
		prompt += "\n请根据以上信息，生成一份简要的监控分析报表，包含：\n1. 告警爆发原因分析\n2. 系统风险评估\n3. 后续优化建议\n请使用 Markdown 格式。"

		// 调用 AI
		content, err := FetchAIResponse(url, key, model, prompt)
		status := "COMPLETED"
		if err != nil {
			content = "生成失败: " + err.Error()
			status = "FAILED"
		}

		models.DB.Model(&models.AIAnalysisReport{}).Where("id = ?", rID).Updates(map[string]interface{}{
			"status":  status,
			"content": content,
		})
	}(report.ID, alarms, NormalizeChatUrl(apiUrl), apiKey, model)

	return &report, nil
}

// NormalizeChatUrl 规范化 Chat 接口地址 (Public for controller usage if needed)
func NormalizeChatUrl(inputUrl string) string {
	inputUrl = strings.TrimSpace(inputUrl)
	if strings.HasSuffix(inputUrl, "/chat/completions") {
		return inputUrl
	}
	// 如果是 /models 结尾，替换
	if strings.HasSuffix(inputUrl, "/models") {
		return strings.Replace(inputUrl, "/models", "/chat/completions", 1)
	}
	// 如果是 /v1 结尾
	if strings.HasSuffix(inputUrl, "/v1") {
		return strings.TrimRight(inputUrl, "/") + "/chat/completions"
	}
	return strings.TrimRight(inputUrl, "/") + "/chat/completions"
}

// 全局 HTTP Client 复用，优化连接池
var aiHttpClient = &http.Client{
	Timeout: 60 * time.Second,
	Transport: &http.Transport{
		MaxIdleConns:        10,
		IdleConnTimeout:     30 * time.Second,
		DisableKeepAlives:   false,
	},
}

// FetchAIResponse 实际调用 (Public for controller usage)
func FetchAIResponse(apiUrl, apiKey, model, prompt string) (string, error) {
	requestBody, _ := json.Marshal(map[string]interface{}{
		"model": model,
		"messages": []map[string]string{
			{"role": "user", "content": prompt},
		},
		"temperature": 0.7,
	})

	req, err := http.NewRequest("POST", apiUrl, bytes.NewBuffer(requestBody))
	if err != nil {
		return "", err
	}
	req.Header.Set("Content-Type", "application/json")
	req.Header.Set("Authorization", "Bearer "+apiKey)

	// 使用全局 Client 复用连接
	resp, err := aiHttpClient.Do(req)
	if err != nil {
		return "", err
	}
	defer resp.Body.Close()

	bodyBytes, _ := io.ReadAll(resp.Body)
	if resp.StatusCode != 200 {
		return "", fmt.Errorf("API Error: %d - %s", resp.StatusCode, string(bodyBytes))
	}

	var result struct {
		Choices []struct {
			Message struct {
				Content string `json:"content"`
			} `json:"message"`
		} `json:"choices"`
		Error struct {
			Message string `json:"message"`
		} `json:"error"`
	}

	if err := json.Unmarshal(bodyBytes, &result); err != nil {
		return "", fmt.Errorf("Parse Error: %v", err)
	}

	if len(result.Choices) > 0 {
		return result.Choices[0].Message.Content, nil
	}

	return "", errors.New("Empty response from AI")
}
