Skip to content

Commit 999a8d9

Browse files
authored
Merge pull request #56 from Hsu-Connect/feat/#55
[#55] Feat: 외부링크 일괄 추가 API 구현
2 parents a1693f8 + 7fb3626 commit 999a8d9

File tree

6 files changed

+87
-6
lines changed

6 files changed

+87
-6
lines changed

src/main/java/hansung/hansung_connect/domain/link/controller/LinkController.java

Lines changed: 23 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,9 @@
11
package hansung.hansung_connect.domain.link.controller;
22

3+
import hansung.hansung_connect.common.response.ApiResponse;
34
import hansung.hansung_connect.domain.link.dto.LinkRequestDTO;
45
import hansung.hansung_connect.domain.link.dto.LinkResponseDTO;
5-
import hansung.hansung_connect.domain.link.service.LinkService;
6+
import hansung.hansung_connect.domain.link.service.LinkCommandService;
67
import io.swagger.v3.oas.annotations.Operation;
78
import io.swagger.v3.oas.annotations.tags.Tag;
89
import jakarta.validation.Valid;
@@ -22,7 +23,7 @@
2223
@RequestMapping("/links")
2324
public class LinkController {
2425

25-
private final LinkService linkService;
26+
private final LinkCommandService linkCommandService;
2627

2728
@Operation(
2829
summary = "링크 추가",
@@ -42,7 +43,7 @@ public ResponseEntity<LinkResponseDTO.LinkResultDTO> createLink(
4243
// 현재 개발 단계이므로 userId 고정함. 추후 수정 예정
4344
Long userId = 1L;
4445

45-
LinkResponseDTO.LinkResultDTO result = linkService.createLink(userId, request);
46+
LinkResponseDTO.LinkResultDTO result = linkCommandService.createLink(userId, request);
4647
return ResponseEntity.status(HttpStatus.CREATED).body(result);
4748
}
4849

@@ -67,7 +68,25 @@ public ResponseEntity<LinkResponseDTO.LinkResultDTO> updateLink(
6768
@Valid @RequestBody LinkRequestDTO.UpdateLinkDTO request
6869
) {
6970
Long userId = 1L; // 개발 단계라 userId 고정
70-
LinkResponseDTO.LinkResultDTO result = linkService.updateLink(userId, linkId, request);
71+
LinkResponseDTO.LinkResultDTO result = linkCommandService.updateLink(userId, linkId, request);
7172
return ResponseEntity.ok(result);
7273
}
74+
75+
@Operation(
76+
summary = "외부링크 일괄 추가",
77+
description = """
78+
여러 개의 외부 링크를 한 번에 추가합니다.
79+
- type: 링크 종류 (LINKEDIN, INSTAGRAM, GITHUB, NOTION, GOOGLE_DRIVE)
80+
- url: 유효한 링크 주소 (예: https://github.com/username)
81+
"""
82+
)
83+
@PostMapping("/batch")
84+
public ApiResponse<LinkResponseDTO.LinkResultListDTO> createLinksBatch(
85+
@Valid @RequestBody LinkRequestDTO.CreateLinksDTO request
86+
) {
87+
// 임시로 userId 고정
88+
Long userId = 1L;
89+
return ApiResponse.onSuccess(linkCommandService.createLinks(userId, request));
90+
}
91+
7392
}

src/main/java/hansung/hansung_connect/domain/link/converter/LinkConverter.java

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,8 +2,10 @@
22

33
import hansung.hansung_connect.domain.link.dto.LinkRequestDTO;
44
import hansung.hansung_connect.domain.link.dto.LinkResponseDTO;
5+
import hansung.hansung_connect.domain.link.dto.LinkResponseDTO.LinkResultDTO;
56
import hansung.hansung_connect.domain.link.entity.Link;
67
import hansung.hansung_connect.domain.user.entity.User;
8+
import java.util.List;
79

810
public class LinkConverter {
911

@@ -26,4 +28,20 @@ public static LinkResponseDTO.LinkResultDTO toLinkResultDTO(Link link) {
2628
public static void applyUpdate(Link link, LinkRequestDTO.UpdateLinkDTO request) {
2729
link.update(request.getType(), request.getUrl());
2830
}
31+
32+
public static List<Link> toLinkList(List<LinkRequestDTO.CreateLinkDTO> requests, User user) {
33+
return requests.stream()
34+
.map(dto -> toLink(dto, user))
35+
.toList();
36+
}
37+
38+
public static LinkResponseDTO.LinkResultListDTO toLinkResultListDTO(List<Link> links) {
39+
List<LinkResultDTO> results = links.stream()
40+
.map(LinkConverter::toLinkResultDTO)
41+
.toList();
42+
43+
return LinkResponseDTO.LinkResultListDTO.builder()
44+
.links(results)
45+
.build();
46+
}
2947
}

src/main/java/hansung/hansung_connect/domain/link/dto/LinkRequestDTO.java

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,9 +2,11 @@
22

33
import hansung.hansung_connect.domain.link.entity.enums.LinkType;
44
import io.swagger.v3.oas.annotations.media.Schema;
5+
import jakarta.validation.Valid;
56
import jakarta.validation.constraints.NotBlank;
67
import jakarta.validation.constraints.NotNull;
78
import jakarta.validation.constraints.Size;
9+
import java.util.List;
810
import lombok.Getter;
911
import lombok.NoArgsConstructor;
1012
import org.hibernate.validator.constraints.URL;
@@ -47,4 +49,16 @@ public static class UpdateLinkDTO {
4749
@URL(message = "유효한 URL 형식이 아닙니다.")
4850
private String url;
4951
}
52+
53+
@Getter
54+
@NoArgsConstructor
55+
public static class CreateLinksDTO {
56+
57+
@Schema(description = "추가할 링크 목록", required = true)
58+
@NotNull(message = "링크 목록은 필수입니다.")
59+
@Size(min = 1, max = 20, message = "링크는 1개 이상 20개 이하로 보내주세요.")
60+
@Valid
61+
private List<CreateLinkDTO> links;
62+
}
63+
5064
}

src/main/java/hansung/hansung_connect/domain/link/dto/LinkResponseDTO.java

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22

33
import hansung.hansung_connect.domain.link.entity.enums.LinkType;
44
import io.swagger.v3.oas.annotations.media.Schema;
5+
import java.util.List;
56
import lombok.AllArgsConstructor;
67
import lombok.Builder;
78
import lombok.Getter;
@@ -24,4 +25,15 @@ public static class LinkResultDTO {
2425
@Schema(description = "등록된 링크 주소", example = "https://github.com/username")
2526
private String url;
2627
}
28+
29+
@Builder
30+
@Getter
31+
@NoArgsConstructor
32+
@AllArgsConstructor
33+
public static class LinkResultListDTO {
34+
35+
@Schema(description = "생성된 링크 결과 목록")
36+
private List<LinkResultDTO> links;
37+
}
38+
2739
}

src/main/java/hansung/hansung_connect/domain/link/service/LinkService.java renamed to src/main/java/hansung/hansung_connect/domain/link/service/LinkCommandService.java

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,9 +3,12 @@
33
import hansung.hansung_connect.domain.link.dto.LinkRequestDTO;
44
import hansung.hansung_connect.domain.link.dto.LinkResponseDTO;
55

6-
public interface LinkService {
6+
public interface LinkCommandService {
77
LinkResponseDTO.LinkResultDTO createLink(Long userId, LinkRequestDTO.CreateLinkDTO request);
88

99
LinkResponseDTO.LinkResultDTO updateLink(Long userId, Long linkId, LinkRequestDTO.UpdateLinkDTO request);
10+
11+
LinkResponseDTO.LinkResultListDTO createLinks(Long userId, LinkRequestDTO.CreateLinksDTO request);
12+
1013
}
1114

src/main/java/hansung/hansung_connect/domain/link/service/LinkServiceImpl.java renamed to src/main/java/hansung/hansung_connect/domain/link/service/LinkCommandServiceImpl.java

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,14 +9,15 @@
99
import hansung.hansung_connect.domain.link.repository.LinkRepository;
1010
import hansung.hansung_connect.domain.user.entity.User;
1111
import hansung.hansung_connect.domain.user.repository.UserRepository;
12+
import java.util.List;
1213
import lombok.RequiredArgsConstructor;
1314
import org.springframework.stereotype.Service;
1415
import org.springframework.transaction.annotation.Transactional;
1516

1617
@Service
1718
@RequiredArgsConstructor
1819
@Transactional(readOnly = true)
19-
public class LinkServiceImpl implements LinkService {
20+
public class LinkCommandServiceImpl implements LinkCommandService {
2021

2122
private final LinkRepository linkRepository;
2223
private final UserRepository userRepository;
@@ -53,5 +54,19 @@ public LinkResponseDTO.LinkResultDTO updateLink(Long userId, Long linkId, LinkRe
5354

5455
return LinkConverter.toLinkResultDTO(link);
5556
}
57+
58+
@Override
59+
@Transactional
60+
public LinkResponseDTO.LinkResultListDTO createLinks(Long userId, LinkRequestDTO.CreateLinksDTO request) {
61+
User user = userRepository.findById(userId)
62+
.orElseThrow(() -> new GeneralException(ErrorStatus.USER_NOT_FOUND));
63+
64+
List<Link> entities = LinkConverter.toLinkList(request.getLinks(), user);
65+
List<Link> saved = linkRepository.saveAll(entities);
66+
67+
return LinkConverter.toLinkResultListDTO(saved);
68+
}
69+
70+
5671
}
5772

0 commit comments

Comments
 (0)