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

import cn.hutool.json.JSONObject;
import com.cool.core.request.R;
import com.cool.modules.dailyreport.entity.DailyReportEntity;
import com.cool.modules.dailyreport.service.DailyReportAiService;
import com.cool.modules.dailyreport.service.DailyReportService;
import com.cool.modules.dailyreport.service.SpeechToTextService;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.Parameter;
import io.swagger.v3.oas.annotations.tags.Tag;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;

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

/**
 * 用户端日报Controller
 */
@Slf4j
@Tag(name = "用户端日报", description = "用户端日报提交和查询")
@RestController
@RequestMapping("/app/dailyreport/report")
@RequiredArgsConstructor
public class AppDailyReportController {

    private final DailyReportService dailyReportService;
    private final SpeechToTextService speechToTextService;
    private final DailyReportAiService dailyReportAiService;

    @Operation(summary = "上传语音并转文字", description = "上传语音文件，后端调用语音识别服务转换为文字")
    @PostMapping("/uploadVoice")
    public R uploadVoice(
            @Parameter(description = "语音文件") @RequestParam("file") MultipartFile file,
            @Parameter(description = "音频格式") @RequestParam(value = "format", defaultValue = "wav") String format
    ) {
        log.info("【用户端日报Controller】上传语音, 文件名: {}, 大小: {} bytes, 格式: {}",
                file.getOriginalFilename(), file.getSize(), format);

        try {
            // 验证文件
            if (file.isEmpty()) {
                log.error("【用户端日报Controller】上传失败：文件为空");
                return R.error("请选择要上传的语音文件");
            }

            // 获取音频数据
            byte[] audioData = file.getBytes();

            // 调用语音识别服务
            String recognizedText = speechToTextService.convertToText(audioData, format);

            log.info("【用户端日报Controller】语音识别成功, 结果长度: {} 字符", recognizedText.length());

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

            return R.ok(result);

        } catch (Exception e) {
            log.error("【用户端日报Controller】语音识别失败", e);
            return R.error("语音识别失败: " + e.getMessage());
        }
    }

    @Operation(summary = "AI格式化日报内容", description = "将用户输入的原始内容通过AI格式化为规范的日报格式")
    @PostMapping("/aiFormat")
    public R aiFormat(@RequestBody JSONObject data) {
        log.info("【用户端日报Controller】AI格式化, 原文长度: {} 字符, 日期: {}",
                data.getStr("originalText") != null ? data.getStr("originalText").length() : 0,
                data.getStr("reportDate"));

        try {
            String originalText = data.getStr("originalText");
            String templateKey = data.getStr("templateKey", "daily_report_format"); // 默认使用 daily_report_format 模板
            String reportDate = data.getStr("reportDate"); // 获取日报日期

            // 验证输入
            if (originalText == null || originalText.trim().isEmpty()) {
                log.error("【用户端日报Controller】AI格式化失败：输入内容为空");
                return R.error("输入内容不能为空");
            }

            // 调用AI格式化服务（带日期参数）
            String formattedContent = dailyReportAiService.formatDailyReport(originalText, templateKey, reportDate);

            log.info("【用户端日报Controller】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("【用户端日报Controller】AI格式化失败", e);
            return R.error("AI格式化失败: " + e.getMessage());
        }
    }

    @Operation(summary = "保存草稿", description = "保存日报草稿，不更改状态为已提交")
    @PostMapping("/saveDraft")
    public R saveDraft(@RequestBody JSONObject data) {
        Long userId = data.getLong("userId");
        log.info("【用户端日报Controller】保存草稿, userId: {}", userId);

        try {
            // 构建日报实体
            DailyReportEntity entity = buildEntityFromRequest(data);
            entity.setStatus(0); // 草稿状态

            // 保存草稿
            DailyReportEntity saved = dailyReportService.saveDraft(entity);

            log.info("【用户端日报Controller】草稿保存成功, id: {}", saved.getId());
            return R.ok(saved);

        } catch (Exception e) {
            log.error("【用户端日报Controller】保存草稿失败", e);
            return R.error("保存草稿失败: " + e.getMessage());
        }
    }

    @Operation(summary = "提交日报", description = "提交日报，标记状态为已提交")
    @PostMapping("/submit")
    public R submit(@RequestBody JSONObject data) {
        Long userId = data.getLong("userId");
        log.info("【用户端日报Controller】提交日报, userId: {}", userId);

        try {
            // 构建日报实体
            DailyReportEntity entity = buildEntityFromRequest(data);

            // 提交日报
            DailyReportEntity submitted = dailyReportService.submitReport(entity);

            log.info("【用户端日报Controller】日报提交成功, id: {}, submitTime: {}",
                    submitted.getId(), submitted.getSubmitTime());
            return R.ok(submitted);

        } catch (Exception e) {
            log.error("【用户端日报Controller】提交日报失败", e);
            return R.error("提交日报失败: " + e.getMessage());
        }
    }

    @Operation(summary = "更新日报", description = "更新已有的日报内容")
    @PostMapping("/update")
    public R update(@RequestBody JSONObject data) {
        Long userId = data.getLong("userId");
        Long reportId = data.getLong("id");
        log.info("【用户端日报Controller】更新日报, userId: {}, reportId: {}", userId, reportId);

        try {
            // 构建日报实体
            DailyReportEntity entity = buildEntityFromRequest(data);
            entity.setId(reportId);

            // 更新日报
            DailyReportEntity updated = dailyReportService.updateReport(entity);

            log.info("【用户端日报Controller】日报更新成功, id: {}", updated.getId());
            return R.ok(updated);

        } catch (Exception e) {
            log.error("【用户端日报Controller】更新日报失败", e);
            return R.error("更新日报失败: " + e.getMessage());
        }
    }

    @Operation(summary = "查询我的日报列表", description = "查询当前用户的日报列表，支持时间范围和状态筛选")
    @GetMapping("/myReports")
    public R getMyReports(
            @Parameter(description = "用户ID") @RequestParam Long userId,
            @Parameter(description = "开始日期 yyyy-MM-dd") @RequestParam(required = false) String startDate,
            @Parameter(description = "结束日期 yyyy-MM-dd") @RequestParam(required = false) String endDate,
            @Parameter(description = "状态 0-草稿 1-已提交") @RequestParam(required = false) Integer status,
            @Parameter(description = "页码") @RequestParam(required = false, defaultValue = "1") Integer page,
            @Parameter(description = "每页大小") @RequestParam(required = false, defaultValue = "20") Integer size
    ) {
        log.info("【用户端日报Controller】查询我的日报列表, userId: {}, startDate: {}, endDate: {}, status: {}, page: {}, size: {}",
                userId, startDate, endDate, status, page, size);

        try {
            // 解析日期
            LocalDate start = startDate != null ? LocalDate.parse(startDate) : null;
            LocalDate end = endDate != null ? LocalDate.parse(endDate) : null;

            // 查询日报列表（暂时不分页，返回全部数据）
            List<DailyReportEntity> reports = dailyReportService.getUserReports(userId, start, end, status);

            log.info("【用户端日报Controller】查询成功, 数量: {}", reports.size());
            return R.ok(reports);

        } catch (Exception e) {
            log.error("【用户端日报Controller】查询我的日报列表失败", e);
            return R.error("查询失败: " + e.getMessage());
        }
    }

    @Operation(summary = "查询日报详情", description = "根据日报ID查询详细信息")
    @GetMapping("/detail")
    public R getDetail(
            @Parameter(description = "日报ID") @RequestParam Long id,
            @Parameter(description = "用户ID") @RequestParam Long userId
    ) {
        log.info("【用户端日报Controller】查询日报详情, id: {}, userId: {}", id, userId);

        try {
            // 查询日报
            DailyReportEntity report = dailyReportService.getById(id);

            if (report == null) {
                log.warn("【用户端日报Controller】日报不存在, id: {}", id);
                return R.error("日报不存在");
            }

            // 验证权限（只能查看自己的日报）
            if (!report.getUserId().equals(userId)) {
                log.error("【用户端日报Controller】无权限查看, userId: {}, ownerId: {}", userId, report.getUserId());
                return R.error("无权限查看此日报");
            }

            log.info("【用户端日报Controller】查询成功");
            return R.ok(report);

        } catch (Exception e) {
            log.error("【用户端日报Controller】查询日报详情失败", e);
            return R.error("查询失败: " + e.getMessage());
        }
    }

    @Operation(summary = "获取今日日报", description = "获取当前用户今天的日报（如果存在）")
    @GetMapping("/todayReport")
    public R getTodayReport(@Parameter(description = "用户ID") @RequestParam Long userId) {
        log.info("【用户端日报Controller】获取今日日报, userId: {}", userId);

        try {
            LocalDate today = LocalDate.now();

            // 查询今日日报
            DailyReportEntity report = dailyReportService.getByUserIdAndDate(userId, today);

            if (report != null) {
                log.info("【用户端日报Controller】今日日报存在, id: {}, status: {}", report.getId(), report.getStatus());
                return R.ok(report);
            } else {
                log.info("【用户端日报Controller】今日暂无日报");
                return R.ok(null);
            }

        } catch (Exception e) {
            log.error("【用户端日报Controller】获取今日日报失败", e);
            return R.error("查询失败: " + e.getMessage());
        }
    }

    /**
     * 从请求数据构建日报实体
     *
     * @param data 请求数据
     * @return 日报实体
     */
    private DailyReportEntity buildEntityFromRequest(JSONObject data) {
        DailyReportEntity entity = new DailyReportEntity();

        entity.setUserId(data.getLong("userId"));

        // 日报日期（默认今天）
        String reportDateStr = data.getStr("reportDate");
        LocalDate reportDate = reportDateStr != null ? LocalDate.parse(reportDateStr) : LocalDate.now();
        entity.setReportDate(reportDate);

        entity.setOriginalText(data.getStr("originalText"));
        entity.setAiFormattedContent(data.getStr("aiFormattedContent"));
        entity.setUserEditedContent(data.getStr("userEditedContent"));
        entity.setAiModelId(data.getLong("aiModelId"));
        entity.setAiTemplateId(data.getLong("aiTemplateId"));
        entity.setInputType(data.getInt("inputType", 0)); // 默认文字输入

        return entity;
    }
}
