package com.gameplatform.server.controller.admin;

import com.gameplatform.server.model.dto.admin.AnnouncementConverter;
import com.gameplatform.server.model.dto.admin.AnnouncementRequest;
import com.gameplatform.server.model.dto.admin.AnnouncementResponse;
import com.gameplatform.server.model.dto.common.PageResult;
import com.gameplatform.server.model.entity.admin.Announcement;
import com.gameplatform.server.service.admin.AnnouncementService;
import com.gameplatform.server.service.admin.AnnouncementByCodeService;
import io.jsonwebtoken.Claims;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.Parameter;
import io.swagger.v3.oas.annotations.tags.Tag;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.ResponseEntity;
import org.springframework.security.core.Authentication;
import org.springframework.web.bind.annotation.*;

import java.util.List;

@RestController
@RequestMapping("/api/admin/announcement")
@Tag(name = "公告管理", description = "系统公告的增删改查接口")
public class AnnouncementController {
    
    private static final Logger logger = LoggerFactory.getLogger(AnnouncementController.class);
    
    @Autowired
    private AnnouncementService announcementService;
    
    @Autowired
    private AnnouncementByCodeService announcementByCodeService;
    
    @PostMapping
    @Operation(summary = "创建公告", description = "创建新的系统公告，belongId会自动从JWT token中获取")
    public ResponseEntity<Object> createAnnouncement(@RequestBody AnnouncementRequest request, Authentication authentication) {
        if (request.getTitle() == null || request.getTitle().trim().isEmpty()) {
            return ResponseEntity.badRequest().body(new Object() {
                public final boolean success = false;
                public final String message = "公告标题不能为空";
            });
        }
        
        if (request.getContent() == null || request.getContent().trim().isEmpty()) {
            return ResponseEntity.badRequest().body(new Object() {
                public final boolean success = false;
                public final String message = "公告内容不能为空";
            });
        }
        
        if (request.getEnabled() == null) {
            request.setEnabled(false); // 默认禁用
        }
        
        // 从JWT token中获取当前用户ID
        if (authentication == null) {
            return ResponseEntity.badRequest().body(new Object() {
                public final boolean success = false;
                public final String message = "用户未认证";
            });
        }
        
        Claims claims = (Claims) authentication.getDetails();
        if (claims == null) {
            return ResponseEntity.badRequest().body(new Object() {
                public final boolean success = false;
                public final String message = "无法获取用户信息";
            });
        }
        
        Long userId = claims.get("userId", Long.class);
        if (userId == null) {
            return ResponseEntity.badRequest().body(new Object() {
                public final boolean success = false;
                public final String message = "无法获取用户ID";
            });
        }
        
        // 设置belongId为当前用户ID
        request.setBelongId(userId.intValue());
        
        Announcement announcement = AnnouncementConverter.toEntity(request);
        boolean success = announcementService.createAnnouncement(announcement);
        final boolean finalSuccess = success;
        
        return ResponseEntity.ok(new Object() {
            public final boolean success = finalSuccess;
            public final String message = finalSuccess ? "公告创建成功" : "公告创建失败";
            public final Long id = finalSuccess ? announcement.getId() : null;
        });
    }
    
    @GetMapping("/list")
    @Operation(summary = "获取公告列表", description = "分页获取所有系统公告")
    public ResponseEntity<PageResult<AnnouncementResponse>> getAnnouncementList(
            @Parameter(description = "页码", example = "1") @RequestParam(defaultValue = "1") int page,
            @Parameter(description = "每页大小", example = "20") @RequestParam(defaultValue = "20") int size,
            @Parameter(description = "按启用状态筛选，不传则获取全部") @RequestParam(required = false) Boolean enabled,
            @Parameter(description = "按归属ID筛选") @RequestParam(required = false) Integer belongId,
            Authentication authentication) {
        
        // 强制按当前用户归属筛选，忽略外部传入的belongId
        Claims claims = (Claims) (authentication != null ? authentication.getDetails() : null);
        if (claims == null) {
            return ResponseEntity.badRequest().build();
        }
        Long userId = claims.get("userId", Long.class);
        if (userId == null) {
            return ResponseEntity.badRequest().build();
        }
        Integer selfBelongId = userId.intValue();

        int offset = (page - 1) * size;
        List<Announcement> announcements;
        long total;
        
        if (enabled != null) {
            announcements = announcementService.getAnnouncementsByBelongIdAndEnabled(selfBelongId, enabled, size, offset);
            total = announcementService.getAnnouncementCountByBelongIdAndEnabled(selfBelongId, enabled);
        } else {
            announcements = announcementService.getAnnouncementsByBelongId(selfBelongId, size, offset);
            total = announcementService.getAnnouncementCountByBelongId(selfBelongId);
        }
        
        List<AnnouncementResponse> responses = announcements.stream()
                .map(AnnouncementConverter::toResponse)
                .toList();
        
        PageResult<AnnouncementResponse> result = new PageResult<>();
        result.setItems(responses);
        result.setTotal(total);
        result.setPage(page);
        result.setSize(size);
        
        return ResponseEntity.ok(result);
    }
    
    @GetMapping("/{id}")
    @Operation(summary = "获取公告详情", description = "根据ID获取公告详细信息")
    public ResponseEntity<AnnouncementResponse> getAnnouncementById(
            @Parameter(description = "公告ID", example = "1") @PathVariable Long id,
            Authentication authentication) {
        Claims claims = (Claims) (authentication != null ? authentication.getDetails() : null);
        if (claims == null) {
            return ResponseEntity.notFound().build();
        }
        Long userId = claims.get("userId", Long.class);
        if (userId == null) {
            return ResponseEntity.notFound().build();
        }
        Announcement announcement = announcementService.getAnnouncementById(id);
        if (announcement == null || announcement.getBelongId() == null || !announcement.getBelongId().equals(userId.intValue())) {
            return ResponseEntity.notFound().build();
        }
        return ResponseEntity.ok(AnnouncementConverter.toResponse(announcement));
    }
    
    @PutMapping("/{id}")
    @Operation(summary = "更新公告", description = "更新指定ID的公告信息，belongId会自动从JWT token中获取")
    public ResponseEntity<Object> updateAnnouncement(
            @Parameter(description = "公告ID", example = "1") @PathVariable Long id,
            @RequestBody AnnouncementRequest request,
            Authentication authentication) {
        
        // 检查公告是否存在
        Announcement existing = announcementService.getAnnouncementById(id);
        if (existing == null) {
            return ResponseEntity.notFound().build();
        }

        // 所有操作仅限本人公告
        Claims claims = (Claims) (authentication != null ? authentication.getDetails() : null);
        if (claims == null) {
            return ResponseEntity.notFound().build();
        }
        Long userId = claims.get("userId", Long.class);
        if (userId == null || existing.getBelongId() == null || !existing.getBelongId().equals(userId.intValue())) {
            return ResponseEntity.notFound().build();
        }

        if (request.getTitle() != null && request.getTitle().trim().isEmpty()) {
            return ResponseEntity.badRequest().body(new Object() {
                public final boolean success = false;
                public final String message = "公告标题不能为空";
            });
        }
        
        if (request.getContent() != null && request.getContent().trim().isEmpty()) {
            return ResponseEntity.badRequest().body(new Object() {
                public final boolean success = false;
                public final String message = "公告内容不能为空";
            });
        }
        
        Announcement announcement = AnnouncementConverter.toEntity(request);
        announcement.setId(id);
        // 禁止通过更新接口修改belongId
        announcement.setBelongId(null);
        boolean success = announcementService.updateAnnouncement(announcement);
        final boolean finalSuccess = success;
        
        return ResponseEntity.ok(new Object() {
            public final boolean success = finalSuccess;
            public final String message = finalSuccess ? "公告更新成功" : "公告更新失败";
        });
    }
    
    @DeleteMapping("/{id}")
    @Operation(summary = "删除公告", description = "删除指定ID的公告")
    public ResponseEntity<Object> deleteAnnouncement(
            @Parameter(description = "公告ID", example = "1") @PathVariable Long id,
            Authentication authentication) {
        
        Announcement existing = announcementService.getAnnouncementById(id);
        if (existing == null) {
            return ResponseEntity.notFound().build();
        }
        Claims claims = (Claims) (authentication != null ? authentication.getDetails() : null);
        if (claims == null) {
            return ResponseEntity.notFound().build();
        }
        Long userId = claims.get("userId", Long.class);
        if (userId == null || existing.getBelongId() == null || !existing.getBelongId().equals(userId.intValue())) {
            return ResponseEntity.notFound().build();
        }
        
        boolean success = announcementService.deleteAnnouncement(id);
        final boolean finalSuccess = success;
        
        return ResponseEntity.ok(new Object() {
            public final boolean success = finalSuccess;
            public final String message = finalSuccess ? "公告删除成功" : "公告删除失败";
        });
    }
    
    @PutMapping("/{id}/enabled")
    @Operation(summary = "更新公告启用状态", description = "启用或禁用指定公告")
    public ResponseEntity<Object> updateAnnouncementEnabled(
            @Parameter(description = "公告ID", example = "1") @PathVariable Long id,
            @Parameter(description = "启用状态", example = "true") @RequestParam Boolean enabled,
            Authentication authentication) {
        
        Announcement existing = announcementService.getAnnouncementById(id);
        if (existing == null) {
            return ResponseEntity.notFound().build();
        }
        Claims claims = (Claims) (authentication != null ? authentication.getDetails() : null);
        if (claims == null) {
            return ResponseEntity.notFound().build();
        }
        Long userId = claims.get("userId", Long.class);
        if (userId == null || existing.getBelongId() == null || !existing.getBelongId().equals(userId.intValue())) {
            return ResponseEntity.notFound().build();
        }
        
        boolean success = announcementService.updateAnnouncementEnabled(id, enabled);
        final boolean finalSuccess = success;
        final Boolean finalEnabled = enabled;
        
        return ResponseEntity.ok(new Object() {
            public final boolean success = finalSuccess;
            public final String message = finalSuccess ? 
                (finalEnabled ? "公告已启用" : "公告已禁用") : 
                "状态更新失败";
        });
    }
    
    @GetMapping("/enabled")
    @Operation(summary = "获取启用的公告", description = "获取所有启用状态的公告，用于前端显示")
    public ResponseEntity<List<AnnouncementResponse>> getEnabledAnnouncements(
            @Parameter(description = "按归属ID筛选") @RequestParam(required = false) Integer belongId,
            Authentication authentication) {
        Claims claims = (Claims) (authentication != null ? authentication.getDetails() : null);
        if (claims == null) {
            return ResponseEntity.ok(List.of());
        }
        Long userId = claims.get("userId", Long.class);
        if (userId == null) {
            return ResponseEntity.ok(List.of());
        }
        Integer selfBelongId = userId.intValue();
        List<Announcement> announcements = announcementService.getEnabledAnnouncementsByBelongId(selfBelongId);
        List<AnnouncementResponse> responses = announcements.stream()
                .map(AnnouncementConverter::toResponse)
                .toList();
        return ResponseEntity.ok(responses);
    }
    
    @GetMapping("/by-code/{codeNo}")
    @Operation(summary = "根据codeNo获取代理商公告", description = "根据链接编号获取对应代理商设置的启用公告")
    public ResponseEntity<Object> getAnnouncementsByCodeNo(
            @Parameter(description = "链接编号", example = "ABC123") @PathVariable String codeNo) {
        
        logger.info("接收到根据codeNo获取代理商公告的请求: {}", codeNo);
        
        try {
            logger.debug("调用服务方法获取公告列表: {}", codeNo);
            List<Announcement> announcements = announcementByCodeService.getAnnouncementsByCodeNo(codeNo);
            
            logger.debug("转换公告实体为响应对象, 公告数量: {}", announcements.size());
            List<AnnouncementResponse> responses = announcements.stream()
                    .map(AnnouncementConverter::toResponse)
                    .toList();
            
            final String finalCodeNo = codeNo;
            logger.info("成功获取代理商公告: codeNo={}, 公告数量={}", codeNo, responses.size());
            
            return ResponseEntity.ok(new Object() {
                public final boolean success = true;
                public final String message = "查询成功";
                public final List<AnnouncementResponse> data = responses;
                public final String codeNo = finalCodeNo;
            });
            
        } catch (IllegalArgumentException e) {
            logger.warn("请求参数错误: codeNo={}, 错误信息={}", codeNo, e.getMessage());
            final String finalCodeNo = codeNo;
            return ResponseEntity.badRequest().body(new Object() {
                public final boolean success = false;
                public final String message = e.getMessage();
                public final String codeNo = finalCodeNo;
            });
        } catch (Exception e) {
            logger.error("根据codeNo获取代理商公告时发生系统错误: codeNo={}", codeNo, e);
            final String finalCodeNo = codeNo;
            return ResponseEntity.internalServerError().body(new Object() {
                public final boolean success = false;
                public final String message = "系统错误：" + e.getMessage();
                public final String codeNo = finalCodeNo;
            });
        }
    }
}
