package gc.mda.kcg.domain.event;

import gc.mda.kcg.auth.AuthPrincipal;
import gc.mda.kcg.domain.event.dto.EventStatusUpdateRequest;
import gc.mda.kcg.permission.annotation.RequirePermission;
import jakarta.validation.Valid;
import lombok.RequiredArgsConstructor;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.domain.Sort;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.web.bind.annotation.*;

import java.util.List;
import java.util.Map;

/**
 * 이벤트 관리 API.
 * 예측 이벤트의 조회, 확인, 상태 변경, 처리 이력을 제공.
 */
@RestController
@RequestMapping("/api/events")
@RequiredArgsConstructor
public class EventController {

    private final EventService eventService;

    /**
     * 이벤트 목록 조회 (필터 + 페이징).
     */
    @GetMapping
    @RequirePermission(resource = "monitoring", operation = "READ")
    public Page<PredictionEvent> getEvents(
            @RequestParam(required = false) String status,
            @RequestParam(required = false) String level,
            @RequestParam(required = false) String category,
            @RequestParam(required = false) String vesselMmsi,
            @RequestParam(defaultValue = "0") int page,
            @RequestParam(defaultValue = "20") int size
    ) {
        return eventService.getEvents(
                status, level, category, vesselMmsi,
                PageRequest.of(page, size, Sort.by(Sort.Direction.DESC, "occurredAt"))
        );
    }

    /**
     * 이벤트 상세 조회.
     */
    @GetMapping("/{id}")
    @RequirePermission(resource = "monitoring", operation = "READ")
    public PredictionEvent getEvent(@PathVariable Long id) {
        return eventService.getEventById(id);
    }

    /**
     * 이벤트 처리 이력 조회.
     */
    @GetMapping("/{id}/workflow")
    @RequirePermission(resource = "monitoring", operation = "READ")
    public List<EventWorkflow> getWorkflowHistory(@PathVariable Long id) {
        return eventService.getEventWorkflowHistory(id);
    }

    /**
     * 이벤트 확인 처리 (NEW → ACK).
     */
    @PatchMapping("/{id}/ack")
    @RequirePermission(resource = "monitoring", operation = "UPDATE")
    public PredictionEvent acknowledgeEvent(@PathVariable Long id) {
        AuthPrincipal principal = currentPrincipal();
        return eventService.acknowledgeEvent(
                id,
                principal != null ? principal.getUserId() : null,
                principal != null ? principal.getUserNm() : null
        );
    }

    /**
     * 이벤트 상태 변경 (범용).
     */
    @PatchMapping("/{id}/status")
    @RequirePermission(resource = "monitoring", operation = "UPDATE")
    public PredictionEvent updateStatus(
            @PathVariable Long id,
            @Valid @RequestBody EventStatusUpdateRequest req
    ) {
        AuthPrincipal principal = currentPrincipal();
        return eventService.updateEventStatus(
                id,
                req.status(),
                principal != null ? principal.getUserId() : null,
                principal != null ? principal.getUserNm() : null,
                req.comment()
        );
    }

    /**
     * 상태별 이벤트 카운트 통계.
     */
    @GetMapping("/stats")
    @RequirePermission(resource = "monitoring", operation = "READ")
    public Map<String, Long> getEventStats() {
        return eventService.getEventStats();
    }

    private AuthPrincipal currentPrincipal() {
        var auth = SecurityContextHolder.getContext().getAuthentication();
        if (auth != null && auth.getPrincipal() instanceof AuthPrincipal p) return p;
        return null;
    }
}
