package com.zioinfo.kintex.system.menu;

import com.zioinfo.kintex.auth.EventAccessGuard;
import com.zioinfo.kintex.auth.KintexPrincipal;
import com.zioinfo.kintex.common.ApiResponse;
import com.zioinfo.kintex.common.audit.Audited;
import com.zioinfo.kintex.system.SystemAccessGuard;
import com.zioinfo.kintex.system.sysuser.SysUserMapper;
import jakarta.validation.Valid;
import org.springframework.security.core.annotation.AuthenticationPrincipal;
import org.springframework.web.bind.annotation.*;

import java.util.List;

/** 메뉴 API. GET /api/common/menus(인증, 역할 트리) · /api/admin/menus/**(ADMIN CRUD). */
@RestController
public class MenuController {

    private final MenuService service;
    private final EventAccessGuard authGuard;
    private final SystemAccessGuard adminGuard;
    private final SysUserMapper sysUserMapper;

    public MenuController(MenuService service, EventAccessGuard authGuard,
                          SystemAccessGuard adminGuard, SysUserMapper sysUserMapper) {
        this.service = service;
        this.authGuard = authGuard;
        this.adminGuard = adminGuard;
        this.sysUserMapper = sysUserMapper;
    }

    @GetMapping("/api/common/menus")
    public ApiResponse<List<MenuDto>> menus(@AuthenticationPrincipal KintexPrincipal principal) {
        authGuard.require(principal);
        String role = sysUserMapper.findRoleCode(principal.userId());
        return ApiResponse.ok(service.tree(role, principal.hallManager()));
    }

    @GetMapping("/api/admin/menus")
    public ApiResponse<List<MenuDto>> all(@AuthenticationPrincipal KintexPrincipal principal) {
        adminGuard.requireAdmin(principal);
        return ApiResponse.ok(service.flat());
    }

    @Audited(action = "MENU_SAVE", targetType = "sys_menu")
    @PostMapping("/api/admin/menus")
    public ApiResponse<Void> save(@AuthenticationPrincipal KintexPrincipal principal,
                                  @Valid @RequestBody MenuDto menu) {
        adminGuard.requireAdmin(principal);
        service.save(menu);
        return ApiResponse.ok(null);
    }

    @Audited(action = "MENU_DELETE", targetType = "sys_menu")
    @DeleteMapping("/api/admin/menus/{id}")
    public ApiResponse<Void> delete(@AuthenticationPrincipal KintexPrincipal principal,
                                    @PathVariable String id) {
        adminGuard.requireAdmin(principal);
        service.delete(id);
        return ApiResponse.ok(null);
    }
}
