package com.cool.modules.weeklyreport.controller.app;

import cn.hutool.json.JSONObject;
import com.cool.core.base.BaseController;
import com.cool.core.request.R;
import com.cool.modules.weeklyreport.entity.WeeklyReportEntity;
import com.cool.modules.weeklyreport.service.WeeklyReportAiService;
import com.cool.modules.weeklyreport.service.WeeklyReportService;
import com.cool.modules.dailyreport.entity.DailyReportEntity;
import com.cool.modules.dailyreport.service.DailyReportService;
import com.cool.modules.dailyreport.service.DailyReportAiService;
import com.mybatisflex.core.query.QueryWrapper;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.tags.Tag;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.web.bind.annotation.*;
import jakarta.servlet.http.HttpServletRequest;

import java.time.DayOfWeek;
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.util.List;
import java.util.Comparator;

import static com.cool.modules.weeklyreport.entity.table.WeeklyReportEntityTableDef.WEEKLY_REPORT_ENTITY;

/**
 * 用户端周报Controller
 */
@Slf4j
@Tag(name = "用户端周报管理", description = "用户端周报提交、查询等功能")
@RestController
@RequestMapping("/app/weeklyreport/report")
@RequiredArgsConstructor
public class AppWeeklyReportController extends BaseController<WeeklyReportService, WeeklyReportEntity> {

    private final WeeklyReportService weeklyReportService;
    private final WeeklyReportAiService weeklyReportAiService;
    private final DailyReportService dailyReportService;
    private final DailyReportAiService dailyReportAiService;

    @Override
    protected void init(HttpServletRequest request, JSONObject requestParams) {
        // 应用端当前未使用通用分页/列表接口，此处无需配置
    }

    @Operation(summary = "提交周报")
    @PostMapping("/submit")
    public R submitWeeklyReport(@RequestBody JSONObject data) {
        log.info("【周报提交】开始提交周报, 请求数据: {}", data);

        try {
            Long userId = data.getLong("userId");
            LocalDate weekStartDate = LocalDate.parse(data.getStr("weekStartDate"));
            LocalDate weekEndDate = LocalDate.parse(data.getStr("weekEndDate"));
            String originalText = data.getStr("originalText");
            String aiFormattedContent = data.getStr("aiFormattedContent");
            String userEditedContent = data.getStr("userEditedContent");
            Integer inputType = data.getInt("inputType", 0);

            log.info("【周报提交】解析参数: userId={}, weekStartDate={}, weekEndDate={}",
                userId, weekStartDate, weekEndDate);

            // 查询当前周是否已有周报
            QueryWrapper qw = QueryWrapper.create()
                .eq(WeeklyReportEntity::getUserId, userId)
                .eq(WeeklyReportEntity::getWeekStartDate, weekStartDate)
                .eq(WeeklyReportEntity::getWeekEndDate, weekEndDate);

            WeeklyReportEntity existingReport = weeklyReportService.getOne(qw);

            WeeklyReportEntity report;
            if (existingReport != null) {
                // 更新已有周报
                log.info("【周报提交】当前周已有周报，执行更新操作, reportId={}", existingReport.getId());
                existingReport.setOriginalText(originalText);
                existingReport.setAiFormattedContent(aiFormattedContent);
                existingReport.setUserEditedContent(userEditedContent);
                existingReport.setInputType(inputType);
                existingReport.setStatus(1); // 已提交
                existingReport.setSubmitTime(LocalDateTime.now());
                weeklyReportService.updateById(existingReport);
                report = existingReport;
            } else {
                // 新增周报
                log.info("【周报提交】当前周无周报，执行新增操作");
                report = new WeeklyReportEntity();
                report.setUserId(userId);
                report.setWeekStartDate(weekStartDate);
                report.setWeekEndDate(weekEndDate);
                report.setOriginalText(originalText);
                report.setAiFormattedContent(aiFormattedContent);
                report.setUserEditedContent(userEditedContent);
                report.setInputType(inputType);
                report.setStatus(1); // 已提交
                report.setSubmitTime(LocalDateTime.now());
                weeklyReportService.save(report);
            }

            log.info("【周报提交】周报提交成功, reportId={}", report.getId());
            return R.ok(report);
        } catch (Exception e) {
            log.error("【周报提交】周报提交失败", e);
            return R.error("周报提交失败: " + e.getMessage());
        }
    }

    @Operation(summary = "保存草稿")
    @PostMapping("/saveDraft")
    public R saveDraft(@RequestBody JSONObject data) {
        log.info("【周报草稿】开始保存草稿, 请求数据: {}", data);

        try {
            Long userId = data.getLong("userId");
            LocalDate weekStartDate = LocalDate.parse(data.getStr("weekStartDate"));
            LocalDate weekEndDate = LocalDate.parse(data.getStr("weekEndDate"));
            String originalText = data.getStr("originalText");
            String aiFormattedContent = data.getStr("aiFormattedContent");
            String userEditedContent = data.getStr("userEditedContent");
            Integer inputType = data.getInt("inputType", 0);

            // 查询当前周是否已有周报
            QueryWrapper qw = QueryWrapper.create()
                .eq(WeeklyReportEntity::getUserId, userId)
                .eq(WeeklyReportEntity::getWeekStartDate, weekStartDate)
                .eq(WeeklyReportEntity::getWeekEndDate, weekEndDate);

            WeeklyReportEntity existingReport = weeklyReportService.getOne(qw);

            WeeklyReportEntity report;
            if (existingReport != null) {
                // 更新已有草稿
                log.info("【周报草稿】当前周已有周报，执行更新操作, reportId={}", existingReport.getId());
                existingReport.setOriginalText(originalText);
                existingReport.setAiFormattedContent(aiFormattedContent);
                existingReport.setUserEditedContent(userEditedContent);
                existingReport.setInputType(inputType);
                weeklyReportService.updateById(existingReport);
                report = existingReport;
            } else {
                // 新增草稿
                log.info("【周报草稿】当前周无周报，执行新增操作");
                report = new WeeklyReportEntity();
                report.setUserId(userId);
                report.setWeekStartDate(weekStartDate);
                report.setWeekEndDate(weekEndDate);
                report.setOriginalText(originalText);
                report.setAiFormattedContent(aiFormattedContent);
                report.setUserEditedContent(userEditedContent);
                report.setInputType(inputType);
                report.setStatus(0); // 草稿
                weeklyReportService.save(report);
            }

            log.info("【周报草稿】草稿保存成功, reportId={}", report.getId());
            return R.ok(report);
        } catch (Exception e) {
            log.error("【周报草稿】草稿保存失败", e);
            return R.error("草稿保存失败: " + e.getMessage());
        }
    }

    @Operation(summary = "获取我的周报列表")
    @GetMapping("/myReports")
    public R getMyWeeklyReports(
            @RequestParam Long userId,
            @RequestParam(required = false) String startDate,
            @RequestParam(required = false) String endDate,
            @RequestParam(required = false) Integer status,
            @RequestParam(required = false, defaultValue = "1") Integer page,
            @RequestParam(required = false, defaultValue = "20") Integer size) {

        log.info("【周报查询】开始查询我的周报列表, userId={}, startDate={}, endDate={}, status={}, page={}, size={}",
            userId, startDate, endDate, status, page, size);

        try {
            QueryWrapper qw = QueryWrapper.create()
                .eq(WeeklyReportEntity::getUserId, userId)
                .orderBy(WEEKLY_REPORT_ENTITY.WEEK_START_DATE, false);

            // 添加时间范围筛选
            if (startDate != null && !startDate.isEmpty()) {
                qw.ge(WeeklyReportEntity::getWeekStartDate, LocalDate.parse(startDate));
            }
            if (endDate != null && !endDate.isEmpty()) {
                qw.le(WeeklyReportEntity::getWeekEndDate, LocalDate.parse(endDate));
            }

            // 添加状态筛选
            if (status != null) {
                qw.eq(WeeklyReportEntity::getStatus, status);
            }

            // 分页查询
            List<WeeklyReportEntity> reports = weeklyReportService.list(qw);

            log.info("【周报查询】查询成功, 数量: {}", reports.size());
            return R.ok(reports);
        } catch (Exception e) {
            log.error("【周报查询】查询失败", e);
            return R.error("查询失败: " + e.getMessage());
        }
    }

    @Operation(summary = "获取周报详情")
    @GetMapping("/detail")
    public R getWeeklyReportDetail(@RequestParam Long id, @RequestParam Long userId) {
        log.info("【周报详情】开始查询周报详情, id={}, userId={}", id, userId);

        try {
            WeeklyReportEntity report = weeklyReportService.getById(id);

            if (report == null) {
                log.warn("【周报详情】周报不存在, id={}", id);
                return R.error("周报不存在");
            }

            // 验证权限
            if (!report.getUserId().equals(userId)) {
                log.warn("【周报详情】无权限查看该周报, userId={}, reportUserId={}", userId, report.getUserId());
                return R.error("无权限查看该周报");
            }

            log.info("【周报详情】查询成功");
            return R.ok(report);
        } catch (Exception e) {
            log.error("【周报详情】查询失败", e);
            return R.error("查询失败: " + e.getMessage());
        }
    }

    @Operation(summary = "获取当前周的周报")
    @GetMapping("/currentWeekReport")
    public R getCurrentWeekReport(@RequestParam Long userId) {
        log.info("【当前周周报】开始查询当前周周报, userId={}", userId);

        try {
            // 计算当前周的周一和周日
            LocalDate today = LocalDate.now();
            LocalDate weekStart = today.with(DayOfWeek.MONDAY);
            LocalDate weekEnd = today.with(DayOfWeek.SUNDAY);

            log.info("【当前周周报】当前周范围: {} - {}", weekStart, weekEnd);

            QueryWrapper qw = QueryWrapper.create()
                .eq(WeeklyReportEntity::getUserId, userId)
                .eq(WeeklyReportEntity::getWeekStartDate, weekStart)
                .eq(WeeklyReportEntity::getWeekEndDate, weekEnd);

            WeeklyReportEntity report = weeklyReportService.getOne(qw);

            if (report != null) {
                log.info("【当前周周报】查询成功, reportId={}", report.getId());
            } else {
                log.info("【当前周周报】当前周暂无周报");
            }

            return R.ok(report);
        } catch (Exception e) {
            log.error("【当前周周报】查询失败", e);
            return R.error("查询失败: " + e.getMessage());
        }
    }

    @Operation(summary = "AI格式化周报")
    @PostMapping("/aiFormat")
    public R aiFormat(@RequestBody JSONObject data) {
        log.info("【周报AI格式化】开始AI格式化, 请求数据: {}", data);

        try {
            String originalText = data.getStr("originalText");
            String templateKey = data.getStr("templateKey", "weekly_report_format");
            String weekStartDate = data.getStr("weekStartDate");
            String weekEndDate = data.getStr("weekEndDate");

            log.info("【周报AI格式化】参数: originalText长度={}, templateKey={}, weekStartDate={}, weekEndDate={}",
                originalText != null ? originalText.length() : 0, templateKey, weekStartDate, weekEndDate);

            String formattedContent = weeklyReportAiService.formatWeeklyReport(
                originalText, templateKey, weekStartDate, weekEndDate);

            log.info("【周报AI格式化】格式化成功, 生成内容长度: {}", formattedContent.length());

            JSONObject result = new JSONObject();
            result.set("formattedContent", formattedContent);
            result.set("length", formattedContent.length());

            return R.ok(result);
        } catch (Exception e) {
            log.error("【周报AI格式化】格式化失败", e);
            return R.error("AI格式化失败: " + e.getMessage());
        }
    }

    @Operation(summary = "基于日报自动生成周报")
    @PostMapping("/generateFromDaily")
    public R generateFromDaily(@RequestBody JSONObject data) {
        log.info("【周报自动生成】开始基于日报生成周报, 请求数据: {}", data);

        try {
            Long userId = data.getLong("userId");
            String templateKey = data.getStr("templateKey", "weekly_report_format");
            String weekStartDate = data.getStr("weekStartDate");
            String weekEndDate = data.getStr("weekEndDate");

            if (userId == null) {
                return R.error("userId不能为空");
            }
            if (weekStartDate == null || weekEndDate == null) {
                return R.error("周范围不能为空");
            }

            LocalDate start = LocalDate.parse(weekStartDate);
            LocalDate end = LocalDate.parse(weekEndDate);

            // 仅聚合本周已提交的日报
            List<DailyReportEntity> dailyList = dailyReportService.getUserReports(userId, start, end, 1);

            if (dailyList == null || dailyList.isEmpty()) {
                log.info("【周报自动生成】本周无已提交日报, userId={}, {}-{}", userId, start, end);
                return R.error("本周没有已提交的日报");
            }

            // 按日期升序，拼接内容（优先用户最终编辑，其次AI格式化，最后原文）
            dailyList.sort(Comparator.comparing(DailyReportEntity::getReportDate));

            StringBuilder source = new StringBuilder();
            for (DailyReportEntity r : dailyList) {
                String content = r.getUserEditedContent();
                if (content == null || content.isEmpty()) {
                    content = r.getAiFormattedContent();
                }
                if (content == null || content.isEmpty()) {
                    content = r.getOriginalText();
                }
                if (content != null && !content.isEmpty()) {
                    source.append("# ")
                          .append(r.getReportDate())
                          .append("\n")
                          .append(content)
                          .append("\n\n");
                }
            }

            if (source.length() == 0) {
                return R.error("本周日报内容为空，无法生成周报");
            }

            String formatted = weeklyReportAiService.formatWeeklyReport(
                source.toString(), templateKey, start.toString(), end.toString()
            );

            JSONObject result = new JSONObject();
            result.set("formattedContent", formatted);
            result.set("length", formatted != null ? formatted.length() : 0);
            result.set("sourceCount", dailyList.size());
            result.set("sourceContent", source.toString());

            log.info("【周报自动生成】生成成功, 聚合日报条数: {}, 生成内容长度: {}",
                dailyList.size(), formatted != null ? formatted.length() : 0);

            return R.ok(result);
        } catch (Exception e) {
            log.error("【周报自动生成】失败", e);
            return R.error("周报自动生成失败: " + e.getMessage());
        }
    }

    @Operation(summary = "获取本周工作建议")
    @GetMapping("/advice")
    public R getWeeklyAdvice(
            @RequestParam Long userId,
            @RequestParam String weekStart
    ) {
        try {
            LocalDate start = LocalDate.parse(weekStart);
            LocalDate end = start.plusDays(6);

            // 优先基于当周“已提交周报”的内容
            QueryWrapper wq = QueryWrapper.create()
                .eq(WeeklyReportEntity::getUserId, userId)
                .eq(WeeklyReportEntity::getWeekStartDate, start)
                .eq(WeeklyReportEntity::getWeekEndDate, end)
                .eq(WeeklyReportEntity::getStatus, 1);
            WeeklyReportEntity weekly = weeklyReportService.getOne(wq);

            String contentForAdvice = null;
            if (weekly != null) {
                String c = weekly.getUserEditedContent();
                if (c == null || c.isBlank()) c = weekly.getAiFormattedContent();
                if (c == null || c.isBlank()) c = weekly.getOriginalText();
                if (c != null && !c.isBlank()) {
                    contentForAdvice = new StringBuilder()
                        .append("# 周报\n")
                        .append(c)
                        .toString();
                }
            }

            // 若无周报内容，则回退到当周“已提交日报”聚合
            if (contentForAdvice == null) {
                List<DailyReportEntity> list = dailyReportService.getUserReports(userId, start, end, 1);
                StringBuilder sb = new StringBuilder();
                for (DailyReportEntity r : list) {
                    String c = r.getUserEditedContent();
                    if (c == null || c.isBlank()) c = r.getAiFormattedContent();
                    if (c == null || c.isBlank()) c = r.getOriginalText();
                    if (c != null && !c.isBlank()) {
                        sb.append("- ").append(r.getReportDate()).append(": ")
                          .append(c).append("\n");
                    }
                }
                contentForAdvice = sb.toString();
            }

            String advice = dailyReportAiService.generateAdvice("user_advice_weekly", contentForAdvice);

            JSONObject result = new JSONObject();
            result.set("userId", userId);
            result.set("weekStart", start.toString());
            result.set("weekEnd", end.toString());
            result.set("adviceText", advice);
            return R.ok(result);
        } catch (Exception e) {
            log.error("【用户端周报】获取本周建议失败", e);
            return R.error("获取本周建议失败: " + e.getMessage());
        }
    }
}
