package com.infoepoch.pms.agent.platform.agent.application;

import com.infoepoch.pms.agent.platform.agent.domain.Agent;
import com.infoepoch.pms.agent.platform.agent.application.dto.CreateAgentRequest;
import com.infoepoch.pms.agent.platform.agent.domain.irepository.IAgentFieldRepository;
import com.infoepoch.pms.agent.platform.agent.domain.irepository.IAgentRepository;
import com.infoepoch.pms.agent.platform.chatbot.domain.irepository.IChatbotAgentsRepository;
import com.infoepoch.pms.agent.platform.model.application.ModelQueryService;
import com.infoepoch.pms.agent.platform.model.domain.AiModelConfig;
import com.infoepoch.pms.agent.platform.model.domain.AiModelProvider;
import com.infoepoch.pms.agent.platform.shared.exception.BusinessException;
import com.infoepoch.pms.agent.platform.shared.response.ResultCode;
import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.extension.ExtendWith;
import org.mockito.InOrder;
import org.mockito.Mock;
import org.mockito.junit.jupiter.MockitoExtension;

import java.math.BigDecimal;
import java.time.LocalDateTime;
import java.util.List;
import java.util.Optional;

import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.jupiter.api.Assertions.assertThrows;
import static org.mockito.Mockito.inOrder;
import static org.mockito.Mockito.when;

@ExtendWith(MockitoExtension.class)
class AgentServiceTest {

    @Mock
    private IAgentRepository agentRepository;

    @Mock
    private IAgentFieldRepository agentFieldRepository;

    @Mock
    private IChatbotAgentsRepository chatbotAgentsRepository;

    @Mock
    private ModelQueryService modelQueryService;

    @Test
    void shouldRejectCreatingAgentWithRerankModelConfig() {
        CreateAgentRequest req = new CreateAgentRequest();
        req.setName("审批助手");
        req.setDescription("处理审批");
        req.setModelConfigId("config-rerank");

        when(agentRepository.existsByName("审批助手")).thenReturn(false);
        when(modelQueryService.getModelConfigOrNull("config-rerank")).thenReturn(rerankConfig());

        AgentService service = new AgentService(agentRepository, agentFieldRepository, chatbotAgentsRepository, modelQueryService);

        BusinessException ex = assertThrows(BusinessException.class, () -> service.create(req));

        assertEquals(ResultCode.PARAM_ERROR, ex.getResultCode());
    }

    @Test
    void shouldDeleteChatbotRelationsBeforeDeletingAgent() {
        LocalDateTime now = LocalDateTime.now();
        Agent agent = Agent.restore(
                "agent-1",
                "请假",
                "desc",
                null,
                null,
                null,
                true,
                now,
                now,
                0,
                List.of()
        );
        when(agentRepository.findById("agent-1")).thenReturn(Optional.of(agent));
        AgentService service = new AgentService(agentRepository, agentFieldRepository, chatbotAgentsRepository, modelQueryService);

        service.delete("agent-1");

        InOrder inOrder = inOrder(chatbotAgentsRepository, agentFieldRepository, agentRepository);
        inOrder.verify(chatbotAgentsRepository).deleteByAgentId("agent-1");
        inOrder.verify(agentFieldRepository).deleteByAgentId("agent-1");
        inOrder.verify(agentRepository).delete("agent-1");
    }

    private AiModelConfig rerankConfig() {
        AiModelProvider provider = AiModelProvider.restore(
                "provider-1",
                "DashScope",
                "DASHSCOPE",
                null,
                "sk-test",
                null,
                "provider",
                true,
                null,
                null,
                LocalDateTime.now(),
                LocalDateTime.now()
        );
        return new AiModelConfig(
                provider,
                "gte-rerank",
                "RERANK",
                "Rerank",
                1024,
                BigDecimal.ONE,
                8,
                256,
                Boolean.TRUE,
                Boolean.TRUE,
                null
        );
    }
}
