package com.label.controller; import com.label.annotation.RequireRole; import com.label.common.auth.TokenPrincipal; import com.label.common.result.PageResult; import com.label.common.result.Result; import com.label.dto.SourceResponse; import com.label.service.SourceService; import io.swagger.v3.oas.annotations.Operation; import io.swagger.v3.oas.annotations.Parameter; import io.swagger.v3.oas.annotations.tags.Tag; import jakarta.servlet.http.HttpServletRequest; import lombok.RequiredArgsConstructor; import org.springframework.http.HttpStatus; import org.springframework.web.bind.annotation.*; import org.springframework.web.multipart.MultipartFile; /** * 原始资料管理接口。 * * 权限设计: * - 上传 / 列表 / 详情:UPLOADER 及以上角色(含 ANNOTATOR、REVIEWER、ADMIN) * - 删除:仅 ADMIN */ @Tag(name = "资料管理", description = "原始资料上传、查询和删除") @RestController @RequestMapping("/label/api/source") @RequiredArgsConstructor public class SourceController { private final SourceService sourceService; /** * 上传文件(multipart/form-data)。 * 返回 201 Created + 资料摘要。 */ @Operation(summary = "上传原始资料", description = "dataType: text,image, video") @PostMapping("/upload") @RequireRole("UPLOADER") @ResponseStatus(HttpStatus.CREATED) public Result upload( @Parameter(description = "上传文件,支持文本、图片、视频", required = true) @RequestParam("file") MultipartFile file, @Parameter(description = "资料类型,可选值:text、image、video", example = "text", required = true) @RequestParam("dataType") String dataType, HttpServletRequest request) { TokenPrincipal principal = (TokenPrincipal) request.getAttribute("__token_principal__"); return Result.success(sourceService.upload(file, dataType, principal)); } /** * 分页查询资料列表。 * UPLOADER 只见自己的资料;ADMIN 见全公司资料。 */ @Operation(summary = "分页查询资料列表") @GetMapping("/list") @RequireRole("UPLOADER") public Result> list( @Parameter(description = "页码,从 1 开始", example = "1") @RequestParam(defaultValue = "1") int page, @Parameter(description = "每页条数", example = "20") @RequestParam(defaultValue = "20") int pageSize, @Parameter(description = "资料类型过滤,可选值:text、image、video", example = "text") @RequestParam(required = false) String dataType, @Parameter(description = "资料状态过滤", example = "PENDING") @RequestParam(required = false) String status, HttpServletRequest request) { TokenPrincipal principal = (TokenPrincipal) request.getAttribute("__token_principal__"); return Result.success(sourceService.list(page, pageSize, dataType, status, principal)); } /** * 查询资料详情(含 15 分钟预签名下载链接)。 */ @Operation(summary = "查询资料详情") @GetMapping("/{id}") @RequireRole("UPLOADER") public Result findById( @Parameter(description = "资料 ID", example = "1001") @PathVariable Long id) { return Result.success(sourceService.findById(id)); } /** * 删除资料(仅 PENDING 状态可删)。 * 同步删除 RustFS 文件及 DB 记录。 */ @Operation(summary = "删除资料") @DeleteMapping("/{id}") @RequireRole("ADMIN") public Result delete( @Parameter(description = "资料 ID", example = "1001") @PathVariable Long id, HttpServletRequest request) { TokenPrincipal principal = (TokenPrincipal) request.getAttribute("__token_principal__"); sourceService.delete(id, principal.getCompanyId()); return Result.success(null); } }