[UPDATE] ProjectBaseSearchRequest 적용 및 projectId 필드 추가 (MinioAttachmentEntity, Service, Controller)

main
bjkim 9 months ago
parent cb31bb11b6
commit e94a85571f

@ -1,20 +1,19 @@
package kr.re.etri.autoflow.controllers; package kr.re.etri.autoflow.controllers;
import io.minio.*;
import io.swagger.v3.oas.annotations.Operation; import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.Parameter; import io.swagger.v3.oas.annotations.Parameter;
import io.swagger.v3.oas.annotations.tags.Tag; import io.swagger.v3.oas.annotations.tags.Tag;
import kr.re.etri.autoflow.entity.MinioAttachmentEntity; import kr.re.etri.autoflow.entity.MinioAttachmentEntity;
import kr.re.etri.autoflow.payload.request.BaseSearchRequest;
import kr.re.etri.autoflow.payload.request.ProjectBaseSearchRequest;
import kr.re.etri.autoflow.service.MinioAttachmentService; import kr.re.etri.autoflow.service.MinioAttachmentService;
import lombok.RequiredArgsConstructor; import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j; import lombok.extern.slf4j.Slf4j;
import org.springdoc.core.annotations.ParameterObject; import org.springdoc.core.annotations.ParameterObject;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.core.io.InputStreamResource;
import org.springframework.data.domain.Page; import org.springframework.data.domain.Page;
import org.springframework.http.HttpStatus; import org.springframework.http.*;
import org.springframework.http.MediaType;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.*; import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile; import org.springframework.web.multipart.MultipartFile;
@ -26,10 +25,13 @@ import java.util.*;
@RequiredArgsConstructor @RequiredArgsConstructor
@Slf4j @Slf4j
@Tag(name = "첨부파일", description = "MinIO 첨부파일 관리 API") @Tag(name = "첨부파일", description = "MinIO 첨부파일 관리 API")
public class AttachmentController { public class MinioAttachmentController {
private final MinioAttachmentService minioAttachmentService; private final MinioAttachmentService minioAttachmentService;
@Value("${kubeflow.url}")
private String kubeflowBaseUrl;
@Operation(summary = "첨부파일 전체 조회") @Operation(summary = "첨부파일 전체 조회")
@GetMapping @GetMapping
public ResponseEntity<List<MinioAttachmentEntity>> getAll() { public ResponseEntity<List<MinioAttachmentEntity>> getAll() {
@ -49,7 +51,7 @@ public class AttachmentController {
@Operation(summary = "검색 및 페이지네이션 첨부파일 목록 조회") @Operation(summary = "검색 및 페이지네이션 첨부파일 목록 조회")
@GetMapping("/search") @GetMapping("/search")
public ResponseEntity<Page<MinioAttachmentEntity>> search( public ResponseEntity<Page<MinioAttachmentEntity>> search(
@ParameterObject @ModelAttribute BaseSearchRequest request, @ParameterObject @ModelAttribute ProjectBaseSearchRequest request,
@Parameter( @Parameter(
description = "첨부파일 구분자. 예: WORKFLOW_STEP, DATASET, TRAINING_SCRIPT", description = "첨부파일 구분자. 예: WORKFLOW_STEP, DATASET, TRAINING_SCRIPT",
example = "WORKFLOW_STEP" example = "WORKFLOW_STEP"
@ -100,6 +102,72 @@ public class AttachmentController {
} }
} }
// @Operation(summary = "파일 업로드 및 Kubeflow 업로드",
// description = "MinIO와 DB에 저장하고 Kubeflow REST API에도 업로드합니다. Kubeflow API 경로는 요청 시 지정 가능")
// @PostMapping(value = "/upload-and-kubeflow", consumes = MediaType.MULTIPART_FORM_DATA_VALUE)
// public ResponseEntity<Map<String, Object>> uploadFileAndKubeflow(
// @Parameter(description = "업로드할 파일") @RequestPart("file") MultipartFile file,
// @RequestPart(value = "path", required = false) String path,
// @RequestParam(value = "refId", required = false) Long refId,
// @RequestParam(value = "refType", required = false, defaultValue = "TRAINING_SCRIPT") String refType,
// @RequestParam(value = "title", required = false) String title,
// @RequestParam(value = "description", required = false) String description,
// @RequestParam(value = "version", required = false, defaultValue = "1") Integer version,
// @RequestParam(value = "regUserId") String regUserId,
// @RequestParam(value = "kubeflowApi") String kubeflowApi
// ) {
// Map<String, Object> response = new HashMap<>();
// try {
// MinioAttachmentEntity saved = minioAttachmentService.uploadFile(
// file, path, refId, refType, title, description, version, regUserId
// );
// String minioUrl = minioAttachmentService.getFileUrl(saved.getStoragePath());
// response.put("attachment", saved);
// response.put("minioUrl", minioUrl);
//
// RestTemplate restTemplate = new RestTemplate();
// MultiValueMap<String, Object> body = new LinkedMultiValueMap<>();
// body.add("uploadfile", new MultipartInputStreamFileResource(file.getInputStream(), file.getOriginalFilename()));
//
// HttpHeaders headers = new HttpHeaders();
// headers.setContentType(MediaType.MULTIPART_FORM_DATA);
//
// HttpEntity<MultiValueMap<String, Object>> requestEntity = new HttpEntity<>(body, headers);
//
// String fullUrl = kubeflowBaseUrl + kubeflowApi;
// ResponseEntity<String> kubeflowResponse = restTemplate.postForEntity(fullUrl, requestEntity, String.class);
//
// response.put("kubeflowResponse", kubeflowResponse.getBody());
//
// return ResponseEntity.ok(response);
//
// } catch (Exception e) {
// log.error("파일 업로드 실패", e);
// response.put("error", e.getMessage());
// return ResponseEntity.status(HttpStatus.INTERNAL_SERVER_ERROR).body(response);
// }
// }
// 파일 업로드용 InputStreamResource
private static class MultipartInputStreamFileResource extends InputStreamResource {
private final String filename;
public MultipartInputStreamFileResource(InputStream inputStream, String filename) {
super(inputStream);
this.filename = filename;
}
@Override
public String getFilename() {
return this.filename;
}
@Override
public long contentLength() {
return -1;
}
}
@Operation(summary = "파일 업데이트", description = "파일을 새 버전으로 업로드합니다. 기존 파일은 그대로 보존되고, 버전은 +1 증가합니다.") @Operation(summary = "파일 업데이트", description = "파일을 새 버전으로 업로드합니다. 기존 파일은 그대로 보존되고, 버전은 +1 증가합니다.")
@PutMapping(value = "/{id}/update", consumes = MediaType.MULTIPART_FORM_DATA_VALUE) @PutMapping(value = "/{id}/update", consumes = MediaType.MULTIPART_FORM_DATA_VALUE)
public ResponseEntity<Map<String, Object>> updateFile( public ResponseEntity<Map<String, Object>> updateFile(

@ -87,4 +87,8 @@ public class MinioAttachmentEntity {
@Comment("파일 설명") @Comment("파일 설명")
@Column(length = 1000) @Column(length = 1000)
private String description; private String description;
@Schema(description = "프로젝트 아이디", example = "1", defaultValue = "0")
@Column(nullable = false)
private Long projectId;
} }

@ -5,6 +5,7 @@ import io.minio.PutObjectArgs;
import jakarta.transaction.Transactional; import jakarta.transaction.Transactional;
import kr.re.etri.autoflow.entity.MinioAttachmentEntity; import kr.re.etri.autoflow.entity.MinioAttachmentEntity;
import kr.re.etri.autoflow.payload.request.BaseSearchRequest; import kr.re.etri.autoflow.payload.request.BaseSearchRequest;
import kr.re.etri.autoflow.payload.request.ProjectBaseSearchRequest;
import kr.re.etri.autoflow.repository.MinioAttachmentRepository; import kr.re.etri.autoflow.repository.MinioAttachmentRepository;
import kr.re.etri.autoflow.specification.MinioAttachmentSpecification; import kr.re.etri.autoflow.specification.MinioAttachmentSpecification;
import lombok.RequiredArgsConstructor; import lombok.RequiredArgsConstructor;
@ -105,7 +106,7 @@ public class MinioAttachmentService {
/** /**
* + * +
*/ */
public Page<MinioAttachmentEntity> search(BaseSearchRequest request, String refType) { public Page<MinioAttachmentEntity> search(ProjectBaseSearchRequest request, String refType) {
int pageIndex = request.getPage() > 0 ? request.getPage() - 1 : 0; int pageIndex = request.getPage() > 0 ? request.getPage() - 1 : 0;
Pageable pageable = PageRequest.of( Pageable pageable = PageRequest.of(
@ -126,6 +127,12 @@ public class MinioAttachmentService {
endDate endDate
); );
if (request.getProjectId() != null) {
spec = spec.and((root, query, cb) ->
cb.equal(root.get("projectId"), request.getProjectId())
);
}
return minioAttachmentRepository.findAll(spec, pageable); return minioAttachmentRepository.findAll(spec, pageable);
} }

Loading…
Cancel
Save