Skip to content

Commit ecefebc

Browse files
authored
feat: 홈 화면 조회 로직 구현
2 parents 4090a3b + bc9a34a commit ecefebc

6 files changed

Lines changed: 172 additions & 1 deletion

File tree

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
package bootcamp.kakao.server.controller;
2+
3+
import bootcamp.kakao.server.common.dto.DataResponseDto;
4+
import bootcamp.kakao.server.common.enums.Code;
5+
import bootcamp.kakao.server.dto.home.HomeResponseDto;
6+
import bootcamp.kakao.server.service.HomeService;
7+
import lombok.RequiredArgsConstructor;
8+
import org.springframework.web.bind.annotation.GetMapping;
9+
import org.springframework.web.bind.annotation.PathVariable;
10+
import org.springframework.web.bind.annotation.RequestMapping;
11+
import org.springframework.web.bind.annotation.RestController;
12+
13+
@RestController
14+
@RequestMapping("/api/home")
15+
@RequiredArgsConstructor
16+
public class HomeController {
17+
18+
private final HomeService homeService;
19+
20+
@GetMapping("/{userId}")
21+
public DataResponseDto<HomeResponseDto> getHomeData(@PathVariable ("userId") Long userId) {
22+
HomeResponseDto homeResponseDto = homeService.getHomeData(userId);
23+
return new DataResponseDto<>(Code.OK, "홈 데이터를 성공적으로 조회하였습니다.", homeResponseDto);
24+
}
25+
}
Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
package bootcamp.kakao.server.dto.home;
2+
3+
import bootcamp.kakao.server.dto.learningsource.LearningSourceResponseDto;
4+
import lombok.Builder;
5+
import lombok.Getter;
6+
7+
import java.util.List;
8+
9+
@Getter
10+
@Builder
11+
public class HomeResponseDto {
12+
13+
private Long userId;
14+
private String nickname;
15+
private List<LearningSourceResponseDto> learningSourceResponseDtos;
16+
}

src/main/java/bootcamp/kakao/server/repository/ChapterRepository.java

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,4 +11,5 @@
1111
public interface ChapterRepository extends JpaRepository<Chapter, Long> {
1212
void deleteByLearningSourceId(Long learningSourceId);
1313
List<Chapter> findAllByLearningSourceId(Long learningSourceId);
14+
List<Chapter> findAllByLearningSourceIdIn(List<Long> learningSourceIds);
1415
}
Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,17 @@
11
package bootcamp.kakao.server.repository;
22

33
import bootcamp.kakao.server.domain.LearningSource;
4+
import bootcamp.kakao.server.domain.User;
5+
import bootcamp.kakao.server.dto.learningsource.LearningSourceResponseDto;
46
import org.springframework.data.jpa.repository.JpaRepository;
57
import org.springframework.stereotype.Repository;
68

9+
import java.util.List;
710
import java.util.Optional;
811

912
@Repository
1013
public interface LearningSourceRepository extends JpaRepository<LearningSource, Long> {
1114

1215
Optional<LearningSource> findByTitle(String title);
16+
List<LearningSource> findAllByUser(User user);
1317
}
Lines changed: 124 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,124 @@
1+
package bootcamp.kakao.server.service;
2+
3+
import bootcamp.kakao.server.common.enums.Code;
4+
import bootcamp.kakao.server.common.exception.GeneralException;
5+
import bootcamp.kakao.server.domain.Chapter;
6+
import bootcamp.kakao.server.domain.LearningSource;
7+
import bootcamp.kakao.server.domain.Task;
8+
import bootcamp.kakao.server.domain.User;
9+
import bootcamp.kakao.server.dto.home.HomeResponseDto;
10+
import bootcamp.kakao.server.dto.learningsource.LearningSourceResponseDto;
11+
import bootcamp.kakao.server.dto.schedule.ChapterInfoDto;
12+
import bootcamp.kakao.server.dto.schedule.TaskInfoDto;
13+
import bootcamp.kakao.server.repository.ChapterRepository;
14+
import bootcamp.kakao.server.repository.LearningSourceRepository;
15+
import bootcamp.kakao.server.repository.TaskRepository;
16+
import bootcamp.kakao.server.repository.UserRepository;
17+
import lombok.RequiredArgsConstructor;
18+
import org.springframework.stereotype.Service;
19+
import org.springframework.transaction.annotation.Transactional;
20+
21+
import java.util.Comparator;
22+
import java.util.List;
23+
import java.util.Map;
24+
import java.util.stream.Collectors;
25+
26+
@Service
27+
@RequiredArgsConstructor
28+
public class HomeService {
29+
30+
private final UserRepository userRepository;
31+
private final LearningSourceRepository learningSourceRepository;
32+
private final ChapterRepository chapterRepository;
33+
private final TaskRepository taskRepository;
34+
35+
@Transactional(readOnly = true)
36+
public HomeResponseDto getHomeData(Long userId) {
37+
38+
User user = userRepository.findById(1L)
39+
.orElseThrow(() -> new GeneralException(Code.NOT_FOUND));
40+
41+
// 1. LearningSource 조회
42+
List<LearningSource> learningSources =
43+
learningSourceRepository.findAllByUser(user);
44+
45+
if (learningSources.isEmpty()) {
46+
return HomeResponseDto.builder()
47+
.userId(user.getId())
48+
.learningSourceResponseDtos(List.of())
49+
.build();
50+
}
51+
52+
List<Long> learningSourceIds = learningSources.stream()
53+
.map(LearningSource::getId)
54+
.toList();
55+
56+
// 2. Chapter 조회
57+
List<Chapter> chapters =
58+
chapterRepository.findAllByLearningSourceIdIn(learningSourceIds);
59+
60+
List<Long> chapterIds = chapters.stream()
61+
.map(Chapter::getId)
62+
.toList();
63+
64+
// 3. Task 조회
65+
List<Task> tasks = chapterIds.isEmpty()
66+
? List.of()
67+
: taskRepository.findAllByChapterIdIn(chapterIds);
68+
69+
// 4. Task → Chapter 기준으로 그룹핑
70+
Map<Long, List<Task>> taskMap =
71+
tasks.stream().collect(Collectors.groupingBy(
72+
task -> task.getChapter().getId()
73+
));
74+
75+
// 5. Chapter → LearningSource 기준으로 그룹핑
76+
Map<Long, List<Chapter>> chapterMap =
77+
chapters.stream().collect(Collectors.groupingBy(
78+
chapter -> chapter.getLearningSource().getId()
79+
));
80+
81+
// 6. DTO 조립
82+
List<LearningSourceResponseDto> learningSourceResponseDtos =
83+
learningSources.stream()
84+
.map(learningSource -> toLearningSourceDto(learningSource, chapterMap, taskMap))
85+
.toList();
86+
87+
return HomeResponseDto.builder()
88+
.userId(user.getId())
89+
.nickname(user.getNickname())
90+
.learningSourceResponseDtos(learningSourceResponseDtos)
91+
.build();
92+
93+
}
94+
95+
private LearningSourceResponseDto toLearningSourceDto(
96+
LearningSource learningSource,
97+
Map<Long, List<Chapter>> chapterMap,
98+
Map<Long, List<Task>> taskMap
99+
) {
100+
List<ChapterInfoDto> chapterDtos =
101+
chapterMap.getOrDefault(learningSource.getId(), List.of())
102+
.stream()
103+
.sorted(Comparator.comparingInt(Chapter::getSortOrder))
104+
.map(chapter -> ChapterInfoDto.builder()
105+
.chapterId(chapter.getId())
106+
.chapterOrder(chapter.getSortOrder())
107+
.chapterTitle(chapter.getTitle())
108+
.taskInfoDtos(
109+
taskMap.getOrDefault(chapter.getId(), List.of())
110+
.stream()
111+
.map(TaskInfoDto::from)
112+
.toList()
113+
)
114+
.build()
115+
)
116+
.toList();
117+
118+
return LearningSourceResponseDto.builder()
119+
.learningSourceTitle(learningSource.getTitle())
120+
.chapterInfoDtos(chapterDtos)
121+
.build();
122+
}
123+
124+
}

src/main/java/bootcamp/kakao/server/service/LearningSourceService.java

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,6 @@
2424
import java.util.stream.Collectors;
2525

2626
@Service
27-
@Transactional
2827
@RequiredArgsConstructor
2928
public class LearningSourceService {
3029

@@ -34,6 +33,7 @@ public class LearningSourceService {
3433
private final FastApiClient fastApiClient;
3534
private final SummaryRepository summaryRepository;
3635

36+
@Transactional(readOnly = true)
3737
public LearningSourceResponseDto getLearningSourceDetails(Long learningSourceId) {
3838

3939
// 1. LearningSource title 가져오기
@@ -74,6 +74,7 @@ public LearningSourceResponseDto getLearningSourceDetails(Long learningSourceId)
7474
.build();
7575
}
7676

77+
@Transactional
7778
public LearningSourceSummaryResponseDto getLearningSourceSummary(Long learningSourceId, Long taskId) {
7879

7980
Task task = taskRepository.findById(taskId)

0 commit comments

Comments
 (0)