package com.rj.controller;

import com.fasterxml.jackson.databind.ObjectMapper;
import com.rj.dto.VideoSynthesisRequestDto;
import lombok.extern.slf4j.Slf4j;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.autoconfigure.web.servlet.AutoConfigureWebMvc;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.http.MediaType;
import org.springframework.test.context.TestPropertySource;
import org.springframework.test.web.servlet.MockMvc;
import org.springframework.test.web.servlet.MvcResult;
import org.springframework.test.web.servlet.setup.MockMvcBuilders;
import org.springframework.web.context.WebApplicationContext;

import static org.junit.jupiter.api.Assertions.*;
import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.*;
import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.*;

/**
 * 视频合成接口测试
 * 
 * @author rj
 * @date 2025-01-02
 */
@SpringBootTest
@AutoConfigureWebMvc
@TestPropertySource(properties = {
    "dashscope.api.key=${DASHSCOPE_API_KEY:test-key}"
})
@Slf4j
public class VideoSynthesisControllerTest {

    @Autowired
    private WebApplicationContext webApplicationContext;

    @Autowired
    private ObjectMapper objectMapper;

    private MockMvc mockMvc;

    @org.junit.jupiter.api.BeforeEach
    void setUp() {
        mockMvc = MockMvcBuilders.webAppContextSetup(webApplicationContext).build();
    }

    /**
     * 测试视频合成接口 - 正常情况
     */
    @Test
    void testSynthesizeVideo_Success() throws Exception {
        log.info("=== 测试视频合成接口 - 正常情况 ===");

        // 构建请求参数
        VideoSynthesisRequestDto requestDto = new VideoSynthesisRequestDto();
        requestDto.setImageUrl("https://example.com/test-image.jpg");
        requestDto.setAudioUrl("https://example.com/test-audio.wav");
        requestDto.setImageId("img-12345");
        requestDto.setAudioId("audio-67890");
        requestDto.setOwnerName("张三");
        requestDto.setOwnerPhone("13800138000");
        requestDto.setModelProvider("dashscope");
        requestDto.setTemplateId("normal");
        requestDto.setEyeMoveFreq(java.math.BigDecimal.valueOf(0.5));
        requestDto.setVideoFps(30);
        requestDto.setMouthMoveStrength(java.math.BigDecimal.valueOf(1.0));
        requestDto.setPasteBack(true);
        requestDto.setHeadMoveStrength(java.math.BigDecimal.valueOf(0.7));

        MvcResult result = mockMvc.perform(post("/api/video-synthesis/synthesize")
                .contentType(MediaType.APPLICATION_JSON)
                .content(objectMapper.writeValueAsString(requestDto)))
                .andExpect(status().isOk())
                .andExpect(content().contentType(MediaType.APPLICATION_JSON))
                .andReturn();

        String responseContent = result.getResponse().getContentAsString();
        log.info("视频合成响应: {}", responseContent);

        // 验证响应内容
        assertNotNull(responseContent);
        assertTrue(responseContent.contains("\"requestId\""));
        assertTrue(responseContent.contains("\"taskId\""));
        assertTrue(responseContent.contains("\"taskStatus\""));
    }

    /**
     * 测试视频合成接口 - 缺少必需参数
     */
    @Test
    void testSynthesizeVideo_MissingRequiredParams() throws Exception {
        log.info("=== 测试视频合成接口 - 缺少必需参数 ===");

        // 测试缺少图片URL
        VideoSynthesisRequestDto requestDto1 = new VideoSynthesisRequestDto();
        requestDto1.setAudioUrl("https://example.com/test-audio.wav");
        
        MvcResult result1 = mockMvc.perform(post("/api/video-synthesis/synthesize")
                .contentType(MediaType.APPLICATION_JSON)
                .content(objectMapper.writeValueAsString(requestDto1)))
                .andExpect(status().isBadRequest())
                .andReturn();

        log.info("缺少图片URL响应: {}", result1.getResponse().getContentAsString());

        // 测试缺少音频URL
        VideoSynthesisRequestDto requestDto2 = new VideoSynthesisRequestDto();
        requestDto2.setImageUrl("https://example.com/test-image.jpg");
        
        MvcResult result2 = mockMvc.perform(post("/api/video-synthesis/synthesize")
                .contentType(MediaType.APPLICATION_JSON)
                .content(objectMapper.writeValueAsString(requestDto2)))
                .andExpect(status().isBadRequest())
                .andReturn();

        log.info("缺少音频URL响应: {}", result2.getResponse().getContentAsString());
    }

    /**
     * 测试查询合成结果接口
     */
    @Test
    void testGetSynthesisResult() throws Exception {
        log.info("=== 测试查询合成结果接口 ===");

        String testRequestId = "test-request-id-12345";

        MvcResult result = mockMvc.perform(get("/api/video-synthesis/result/{requestId}", testRequestId))
                .andExpect(status().isNotFound()) // 由于测试数据不存在，应该返回404
                .andReturn();

        String responseContent = result.getResponse().getContentAsString();
        log.info("查询合成结果响应: {}", responseContent);
    }

    /**
     * 测试根据任务ID查询结果接口
     */
    @Test
    void testGetSynthesisResultByTaskId() throws Exception {
        log.info("=== 测试根据任务ID查询结果接口 ===");

        String testTaskId = "test-task-id-12345";

        MvcResult result = mockMvc.perform(get("/api/video-synthesis/result/task/{taskId}", testTaskId))
                .andExpect(status().isNotFound()) // 由于测试数据不存在，应该返回404
                .andReturn();

        String responseContent = result.getResponse().getContentAsString();
        log.info("根据任务ID查询结果响应: {}", responseContent);
    }

    /**
     * 测试视频合成接口 - 使用默认参数
     */
    @Test
    void testSynthesizeVideo_WithDefaultParams() throws Exception {
        log.info("=== 测试视频合成接口 - 使用默认参数 ===");

        // 构建请求参数（只设置必需参数，其他使用默认值）
        VideoSynthesisRequestDto requestDto = new VideoSynthesisRequestDto();
        requestDto.setImageUrl("https://example.com/test-image.jpg");
        requestDto.setAudioUrl("https://example.com/test-audio.wav");

        MvcResult result = mockMvc.perform(post("/api/video-synthesis/synthesize")
                .contentType(MediaType.APPLICATION_JSON)
                .content(objectMapper.writeValueAsString(requestDto)))
                .andExpect(status().isOk())
                .andExpect(content().contentType(MediaType.APPLICATION_JSON))
                .andReturn();

        String responseContent = result.getResponse().getContentAsString();
        log.info("使用默认参数响应: {}", responseContent);

        // 验证响应内容
        assertNotNull(responseContent);
        assertTrue(responseContent.contains("\"requestId\""));
    }

    /**
     * 测试视频合成接口 - 自定义参数
     */
    @Test
    void testSynthesizeVideo_WithCustomParams() throws Exception {
        log.info("=== 测试视频合成接口 - 自定义参数 ===");

        // 构建自定义参数
        VideoSynthesisRequestDto requestDto = new VideoSynthesisRequestDto();
        requestDto.setImageUrl("https://example.com/custom-image.jpg");
        requestDto.setAudioUrl("https://example.com/custom-audio.wav");
        requestDto.setTemplateId("custom");
        requestDto.setEyeMoveFreq(java.math.BigDecimal.valueOf(0.8));
        requestDto.setVideoFps(25);
        requestDto.setMouthMoveStrength(java.math.BigDecimal.valueOf(1.2));
        requestDto.setPasteBack(false);
        requestDto.setHeadMoveStrength(java.math.BigDecimal.valueOf(0.9));

        MvcResult result = mockMvc.perform(post("/api/video-synthesis/synthesize")
                .contentType(MediaType.APPLICATION_JSON)
                .content(objectMapper.writeValueAsString(requestDto)))
                .andExpect(status().isOk())
                .andExpect(content().contentType(MediaType.APPLICATION_JSON))
                .andReturn();

        String responseContent = result.getResponse().getContentAsString();
        log.info("自定义参数响应: {}", responseContent);

        // 验证响应内容
        assertNotNull(responseContent);
        assertTrue(responseContent.contains("\"requestId\""));
    }
}
