package com.wok.supportbot.controller; import com.wok.supportbot.service.CustomerServiceRoleService; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.http.ResponseEntity; import org.springframework.security.access.prepost.PreAuthorize; import org.springframework.web.bind.annotation.DeleteMapping; import org.springframework.web.bind.annotation.GetMapping; import org.springframework.web.bind.annotation.PathVariable; import org.springframework.web.bind.annotation.PostMapping; import org.springframework.web.bind.annotation.PutMapping; import org.springframework.web.bind.annotation.RequestBody; import org.springframework.web.bind.annotation.RequestParam; import org.springframework.web.bind.annotation.RestController; import java.util.List; import java.util.Map; import java.util.Objects; @RestController public class CustomerServiceRoleController { @Autowired private CustomerServiceRoleService customerServiceRoleService; @GetMapping("/role/list") @PreAuthorize("hasRole('admin')") public ResponseEntity> listRoles() { return ResponseEntity.ok(Map.of( "success", true, "data", customerServiceRoleService.listRoles(false) )); } /** * 管理用:列出全部角色(含已停用)。 */ @GetMapping("/role/all") @PreAuthorize("hasRole('admin')") public ResponseEntity> listAllRoles() { return ResponseEntity.ok(Map.of( "success", true, "data", customerServiceRoleService.listRoles(true) )); } @PostMapping("/role") @PreAuthorize("hasRole('admin')") public ResponseEntity> createRole(@RequestBody Map body) { try { customerServiceRoleService.createRole( str(body.get("roleKey")), str(body.get("name")), str(body.get("description")), str(body.get("prompt")), boolOrNull(body.get("enabled"))); return ResponseEntity.ok(Map.of("success", true, "message", "角色创建成功")); } catch (Exception e) { return ResponseEntity.status(500).body(Map.of("success", false, "message", "创建角色失败:" + e.getMessage())); } } @PutMapping("/role/{id}") @PreAuthorize("hasRole('admin')") public ResponseEntity> updateRole(@PathVariable("id") Long roleId, @RequestBody Map body) { try { customerServiceRoleService.updateRole(roleId, str(body.get("name")), str(body.get("description")), str(body.get("prompt")), boolOrNull(body.get("enabled"))); return ResponseEntity.ok(Map.of("success", true, "message", "角色更新成功")); } catch (Exception e) { return ResponseEntity.status(500).body(Map.of("success", false, "message", "更新角色失败:" + e.getMessage())); } } @DeleteMapping("/role/{id}") @PreAuthorize("hasRole('admin')") public ResponseEntity> deleteRole(@PathVariable("id") Long roleId) { try { customerServiceRoleService.deleteRole(roleId); return ResponseEntity.ok(Map.of("success", true, "message", "角色删除成功")); } catch (Exception e) { return ResponseEntity.status(500).body(Map.of("success", false, "message", "删除角色失败:" + e.getMessage())); } } @PutMapping("/role/{id}/categories") @PreAuthorize("hasRole('admin')") public ResponseEntity> updateRoleCategories( @PathVariable("id") Long roleId, @RequestBody Map body) { List categoryIds = parseCategoryIds(body.get("categoryIds")); customerServiceRoleService.updateRoleCategories(roleId, categoryIds); return ResponseEntity.ok(Map.of( "success", true, "message", "更新成功" )); } /** * 更新角色的 MCP 工具权限。 * body: { "allowedMcpTools": ["*"] } 或 { "allowedMcpTools": ["mcp_get_weather", "mcp_query_db"] } */ @SuppressWarnings("unchecked") @PutMapping("/role/{id}/mcp-tools") @PreAuthorize("hasRole('admin')") public ResponseEntity> updateRoleMcpTools( @PathVariable("id") Long roleId, @RequestBody Map body) { try { Object raw = body.get("allowedMcpTools"); List allowedMcpTools; if (raw instanceof List list) { allowedMcpTools = list.stream() .filter(Objects::nonNull) .map(Objects::toString) .distinct() .toList(); } else { allowedMcpTools = List.of(); } customerServiceRoleService.updateRoleMcpTools(roleId, allowedMcpTools); return ResponseEntity.ok(Map.of("success", true, "message", "MCP 工具权限更新成功")); } catch (Exception e) { return ResponseEntity.status(500).body(Map.of("success", false, "message", "更新失败:" + e.getMessage())); } } private List parseCategoryIds(Object rawCategoryIds) { if (!(rawCategoryIds instanceof List list)) { return List.of(); } return list.stream() .filter(Objects::nonNull) .map(item -> item instanceof Number number ? number.longValue() : Long.parseLong(item.toString())) .filter(id -> id > 0) .distinct() .toList(); } private static String str(Object v) { return v == null ? null : v.toString(); } private static Integer intOrNull(Object v) { return v instanceof Number number ? number.intValue() : null; } private static Boolean boolOrNull(Object v) { if (v instanceof Boolean b) { return b; } return v != null ? Boolean.parseBoolean(v.toString()) : null; } }