package utils

import (
	"fmt"

	memorymodel "github.com/LoveLosita/smartflow/backend/memory/model"
)

// AggregateComparisons 把一轮 LLM 比对结果汇总为最终动作。
//
// 职责边界：
// 1. 纯确定性逻辑，不调 LLM，不调外部服务；
// 2. 按优先级从高到低判定：duplicate > update > conflict > unrelated；
// 3. 多条 update 时选 Score 最高的候选执行 UPDATE。
//
// 汇总规则：
// 1. 出现 duplicate → 最终动作 NONE（新 fact 完全重复，不需要写入）；
// 2. 出现 update → 最终动作 UPDATE（更新 Score 最高的那条旧记忆）；
// 3. 出现 conflict → 最终动作 DELETE + 后续按 ADD 处理（旧记忆过时，先删旧的再写新的）；
// 4. 全部 unrelated → 最终动作 ADD（没有相关旧记忆，直接新增）。
func AggregateComparisons(
	fact memorymodel.NormalizedFact,
	comparisons []memorymodel.ComparisonResult,
	candidates []memorymodel.CandidateSnapshot,
) *memorymodel.FinalDecision {
	// 1. 无候选时直接 ADD，无需走任何判断。
	if len(comparisons) == 0 {
		return &memorymodel.FinalDecision{
			Action: memorymodel.DecisionActionAdd,
			Reason: "无相关旧记忆，直接新增",
		}
	}

	// 2. 建立 memoryID → CandidateSnapshot 映射，用于查找 Score。
	snapshotMap := make(map[int64]memorymodel.CandidateSnapshot, len(candidates))
	for _, c := range candidates {
		snapshotMap[c.MemoryID] = c
	}

	hasDuplicate := false
	var bestUpdate *memorymodel.ComparisonResult
	bestUpdateScore := -1.0
	var conflictResult *memorymodel.ComparisonResult

	for i := range comparisons {
		comp := &comparisons[i]

		switch comp.Relation {
		case memorymodel.RelationDuplicate:
			// 3. 出现一条 duplicate 即可确定最终动作为 NONE。
			hasDuplicate = true

		case memorymodel.RelationUpdate:
			// 4. 多条 update 时，选 Score 最高的那条执行 UPDATE。
			snapshot, ok := snapshotMap[comp.MemoryID]
			score := 0.0
			if ok {
				score = snapshot.Score
			}
			if score > bestUpdateScore {
				bestUpdateScore = score
				bestUpdate = comp
			}

		case memorymodel.RelationConflict:
			// 5. 记录第一条 conflict，用于后续 DELETE + ADD 处理。
			if conflictResult == nil {
				conflictResult = comp
			}
		}
	}

	// 6. 按优先级判定最终动作。
	if hasDuplicate {
		return &memorymodel.FinalDecision{
			Action: memorymodel.DecisionActionNone,
			Reason: "存在完全重复的旧记忆，跳过写入",
		}
	}

	if bestUpdate != nil {
		// 7. UPDATE 动作：使用 LLM 提供的合并后内容。
		title := bestUpdate.UpdatedTitle
		if title == "" {
			title = fact.Title
		}
		content := bestUpdate.UpdatedContent
		reason := bestUpdate.Reason
		if reason == "" {
			reason = "新事实是对旧记忆的修正或补充"
		}
		return &memorymodel.FinalDecision{
			Action:   memorymodel.DecisionActionUpdate,
			TargetID: bestUpdate.MemoryID,
			Title:    title,
			Content:  content,
			Reason:   fmt.Sprintf("更新旧记忆(id=%d): %s", bestUpdate.MemoryID, reason),
		}
	}

	if conflictResult != nil {
		// 8. conflict → 先 DELETE 旧记忆，后续由上层按 ADD 写入新 fact。
		return &memorymodel.FinalDecision{
			Action:   memorymodel.DecisionActionDelete,
			TargetID: conflictResult.MemoryID,
			Reason:   fmt.Sprintf("旧记忆(id=%d)与新事实冲突，删除后新增: %s", conflictResult.MemoryID, conflictResult.Reason),
		}
	}

	// 9. 全部 unrelated → 直接 ADD。
	return &memorymodel.FinalDecision{
		Action: memorymodel.DecisionActionAdd,
		Reason: "无相关旧记忆，直接新增",
	}
}
