package cn.nianxx.thhotel.integrations.ai.superagent.control;

import cn.nianxx.thhotel.integrations.ai.superagent.common.request.SuperAgentTaskResultSecurityRequest;
import cn.nianxx.thhotel.integrations.ai.superagent.service.SuperAgentTaskResultSecurityService;
import cn.nianxx.thhotel.integrations.ai.superagent.service.impl.SuperAgentTaskResultException;
import cn.nianxx.thhotel.integrations.ai.superagent.service.impl.SuperAgentTaskResultProperties;
import cn.nianxx.thhotel.workflows.reservation.common.result.SuperAgentTaskResultResponse;
import cn.nianxx.thhotel.workflows.reservation.service.ReservationAiTaskIntakeService;
import java.nio.charset.StandardCharsets;
import org.springframework.http.HttpStatus;
import org.springframework.http.MediaType;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestHeader;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

/**
 * SuperAgent 任务结果入站接口。Controller 只处理外部协议、安全校验和请求分发。
 */
@RestController
@RequestMapping("/api/integrations/superagent/task-results")
public class SuperAgentTaskResultController {

    private static final String REQUEST_PATH = "/api/integrations/superagent/task-results";

    private final SuperAgentTaskResultSecurityService securityService;
    private final SuperAgentTaskResultProperties properties;
    private final ReservationAiTaskIntakeService intakeService;

    /**
     * 注入 SuperAgent 安全服务和 Reservation 接收服务，避免 Controller 直接访问业务持久化层。
     */
    public SuperAgentTaskResultController(
            SuperAgentTaskResultSecurityService securityService,
            SuperAgentTaskResultProperties properties,
            ReservationAiTaskIntakeService intakeService) {
        this.securityService = securityService;
        this.properties = properties;
        this.intakeService = intakeService;
    }

    /**
     * 接收 SuperAgent AI 任务结果，先限制请求体大小，再完成 HMAC 鉴权，最后委托业务服务创建 CP1-3 数据。
     */
    @PostMapping(consumes = MediaType.APPLICATION_JSON_VALUE, produces = MediaType.APPLICATION_JSON_VALUE)
    public ResponseEntity<SuperAgentTaskResultResponse> accept(
            @RequestBody(required = false) String rawBody,
            @RequestHeader(name = "X-TH-Hotel-SuperAgent-Client-Id", required = false) String clientId,
            @RequestHeader(name = "X-TH-Hotel-SuperAgent-Timestamp", required = false) String timestamp,
            @RequestHeader(name = "X-TH-Hotel-SuperAgent-Nonce", required = false) String nonce,
            @RequestHeader(name = "X-TH-Hotel-SuperAgent-Signature", required = false) String signature,
            @RequestHeader(name = "X-TH-Hotel-Request-Id", required = false) String requestId) {
        String requestBody = rawBody == null ? "" : rawBody;
        rejectBodyWhenTooLarge(requestBody);
        securityService.verify(new SuperAgentTaskResultSecurityRequest(
                "POST",
                REQUEST_PATH,
                clientId,
                timestamp,
                nonce,
                signature,
                requestBody
        ));
        SuperAgentTaskResultResponse response = intakeService.accept(requestBody, clientId, requestId);
        HttpStatus status = response.idempotentReplay() ? HttpStatus.OK : HttpStatus.CREATED;
        return ResponseEntity.status(status).body(response);
    }

    /**
     * 在解析 JSON 和校验 Header 之前限制请求体大小，避免超限请求进入后续处理。
     */
    private void rejectBodyWhenTooLarge(String rawBody) {
        long maxBodyBytes = properties.getMaxBodyBytes();
        int actualBytes = rawBody.getBytes(StandardCharsets.UTF_8).length;
        if (maxBodyBytes >= 0 && actualBytes > maxBodyBytes) {
            throw new SuperAgentTaskResultException(
                    HttpStatus.PAYLOAD_TOO_LARGE,
                    "REQUEST_BODY_TOO_LARGE",
                    "请求体超过允许大小。");
        }
    }
}
