Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Refactor: 마이페이지 쿼리 최적화 및 요청 사항 반영 #317

Merged
merged 4 commits into from
Jan 20, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -54,8 +54,9 @@ public ApiResponse<MemberResponseDTO.MemberImageDTO> getProfileImage(@PathVariab
@GetMapping("/profile/{member_id}")
@Operation(summary = "사용자 프로필 기본 정보 조회", description = "마이페이지 사용자 정보 조회 기능")
public ApiResponse<MemberResponseDTO.SimpleMemberDTO> getUserProfile(@AuthenticationPrincipal CustomMemberDetails memberDetails, @PathVariable(value = "member_id") Long memberId){
Member currentMember = memberQueryService.getUserInfo(memberDetails.getId());
Member user = memberQueryService.getUserProfile(memberId);
return ApiResponse.onSuccess(SuccessStatus.MEMBER_OK, MemberConverter.toSimpleMemberResponseDto(user, user));
return ApiResponse.onSuccess(SuccessStatus.MEMBER_OK, MemberConverter.toSimpleMemberResponseDto(currentMember, user));
}

@PutMapping("/info")
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,13 @@ public record TokenRefreshResponseDTO(
@JsonInclude(JsonInclude.Include.NON_NULL)
@JsonNaming(PropertyNamingStrategies.SnakeCaseStrategy.class)
@Builder
public record MemberImageDTO(String url) {}
public record MemberImageDTO(String url) {
public static MemberImageDTO of(String url) {
return MemberImageDTO.builder()
.url(url)
.build();
}
}

@JsonInclude(JsonInclude.Include.NON_NULL)
@JsonNaming(PropertyNamingStrategies.SnakeCaseStrategy.class)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,8 +10,6 @@ public interface MemberRepository extends JpaRepository<Member, Long>, MemberRep

Boolean existsByNickname(String nickname);

Optional<Member> findByEmail(String email);

Optional<Member> findByNicknameIgnoreCase(String nickname);

//Optional<Member> findByNickname(String nickname);
Expand Down
Original file line number Diff line number Diff line change
@@ -1,10 +1,13 @@
package com.codiary.backend.domain.member.repository;

import com.codiary.backend.domain.member.dto.response.MemberResponseDTO;
import com.codiary.backend.domain.member.entity.Member;

import java.util.Optional;

public interface MemberRepositoryCustom {
Optional<Member> findByEmail(String email);

Optional<Member> findMemberWithTechStacksAndProjectsAndTeam(Long userId);
Optional<Member> findMemberWithTechStacks(Long userId);

Expand All @@ -14,4 +17,5 @@ public interface MemberRepositoryCustom {
Optional<Member> findByIdWithFollowings(Long id);
Optional<Member> findByIdWithFollowers(Long id);
Optional<Member> findByIdWithCategory(Long id);
MemberResponseDTO.MemberImageDTO findProfileImageUrl(Long id);
}
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package com.codiary.backend.domain.member.repository;

import com.codiary.backend.domain.member.dto.response.MemberResponseDTO;
import com.codiary.backend.domain.member.entity.Member;
import com.codiary.backend.domain.team.entity.TeamMember;
import com.codiary.backend.domain.project.entity.Project;
Expand All @@ -12,6 +13,7 @@
import static com.codiary.backend.domain.category.entity.QCategory.category;
import static com.codiary.backend.domain.member.entity.QMember.member;
import static com.codiary.backend.domain.member.entity.QMemberCategory.memberCategory;
import static com.codiary.backend.domain.member.entity.QMemberImage.memberImage;
import static com.codiary.backend.domain.techstack.entity.QTechStacks.techStacks;
import static com.codiary.backend.domain.project.entity.QProject.project;
import static com.codiary.backend.domain.team.entity.QTeamMember.teamMember;
Expand All @@ -22,6 +24,16 @@ public class MemberRepositoryImpl implements MemberRepositoryCustom {

private final JPAQueryFactory queryFactory;

public Optional<Member> findByEmail(String email){
Member fetchedMember = queryFactory
.selectFrom(member)
.leftJoin(member.image, memberImage).fetchJoin()
.where(member.email.eq(email))
.fetchOne();

return Optional.ofNullable(fetchedMember);
}

public Optional<Member> findMemberWithTechStacksAndProjectsAndTeam(Long userId) {
Member fetchedMember = queryFactory
.selectFrom(member)
Expand All @@ -39,6 +51,7 @@ public Optional<Member> findMemberWithTechStacks(Long userId) {
Member fetchedMember = queryFactory
.selectFrom(member)
.leftJoin(member.techStackList, techStacks).fetchJoin()
.leftJoin(member.image, memberImage).fetchJoin()
.where(member.memberId.eq(userId))
.fetchOne();

Expand All @@ -60,6 +73,7 @@ public Optional<Member> findByIdWithAndFollowersAndFollowings(Long id) {
.selectFrom(member)
.leftJoin(member.followers)
.leftJoin(member.followings)
.leftJoin(member.image, memberImage).fetchJoin()
.where(member.memberId.eq(id))
.fetchOne();

Expand All @@ -70,6 +84,7 @@ public Optional<Member> findByIdWithFollowings(Long id) {
Member fetchedMember = queryFactory
.selectFrom(member)
.leftJoin(member.followings)
.leftJoin(member.image, memberImage).fetchJoin()
.where(member.memberId.eq(id))
.fetchOne();

Expand All @@ -80,6 +95,7 @@ public Optional<Member> findByIdWithFollowers(Long id) {
Member fetchedMember = queryFactory
.selectFrom(member)
.leftJoin(member.followers)
.leftJoin(member.image, memberImage).fetchJoin()
.where(member.memberId.eq(id))
.fetchOne();

Expand Down Expand Up @@ -116,4 +132,14 @@ public Optional<Member> findByIdWithCategory(Long id) {

return Optional.ofNullable(fetchedMember);
}

public MemberResponseDTO.MemberImageDTO findProfileImageUrl(Long id) {
Optional<String> imageUrl = Optional.ofNullable(queryFactory
.select(member.image.imageUrl)
.from(member)
.where(member.memberId.eq(id))
.fetchOne());

return MemberResponseDTO.MemberImageDTO.of(imageUrl.orElse(""));
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -7,13 +7,14 @@
import com.codiary.backend.global.apiPayload.code.status.ErrorStatus;
import com.codiary.backend.global.apiPayload.exception.GeneralException;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;
import java.util.stream.Collectors;


@Slf4j
@Service
@RequiredArgsConstructor
@Transactional(readOnly = true)
Expand All @@ -24,6 +25,7 @@ public class FollowService {
@Transactional
public Follow follow(Long toId, Member fromMember) {
//Validation: fromMember와 toMember 존재 여부 확인/ 자기 자신 팔로우 불가/ 이미 팔로우 중인지 확인

fromMember = memberRepository.findByIdWithAndFollowersAndFollowings(fromMember.getMemberId()).orElseThrow(() -> new GeneralException(ErrorStatus.MEMBER_NOT_FOUND));

Member toMember = memberRepository.findByIdWithFollowers(toId)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@
import com.codiary.backend.domain.member.repository.MemberRepository;
import com.codiary.backend.domain.techstack.entity.TechStacks;
import com.codiary.backend.domain.techstack.enumerate.TechStack;
import com.codiary.backend.domain.techstack.repository.TechStackRepository;
import com.codiary.backend.global.apiPayload.ApiResponse;
import com.codiary.backend.global.apiPayload.code.status.ErrorStatus;
import com.codiary.backend.global.apiPayload.code.status.SuccessStatus;
Expand All @@ -22,9 +23,11 @@
import java.util.Optional;
import java.util.UUID;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

@Slf4j
@Service
@RequiredArgsConstructor
@Transactional(readOnly = true)
Expand All @@ -34,6 +37,7 @@ public class MemberCommandService {
private final UuidRepository uuidRepository;
private final AmazonS3Manager s3Manager;
private final MemberImageRepository memberImageRepository;
private final TechStackRepository techStackRepository;

@Transactional
public Member getRequester() {
Expand Down Expand Up @@ -93,10 +97,9 @@ public Member addTechStack(Long memberId, TechStack techstack) {
Member member = memberRepository.findMemberWithTechStacks(memberId)
.orElseThrow(() -> new GeneralException(ErrorStatus.MEMBER_NOT_FOUND));

if (member.getTechStackList().stream().anyMatch(stack -> stack.getName().equals(techstack))) {
if (techStackRepository.existsByNameAndMember(techstack, member)) {
throw new GeneralException(ErrorStatus.TECH_STACK_ALREADY_EXISTS);
}

//business logic: 기술스택 추가
List<TechStacks> techStackList = Optional.of(member.getTechStackList()).orElse(new ArrayList<>());
TechStacks newTechStack = new TechStacks(techstack, member);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,6 @@
import com.codiary.backend.global.apiPayload.code.status.ErrorStatus;
import com.codiary.backend.global.apiPayload.code.status.SuccessStatus;
import com.codiary.backend.global.apiPayload.exception.GeneralException;
import com.codiary.backend.global.apiPayload.exception.handler.MemberHandler;
import com.codiary.backend.domain.member.entity.Member;
import com.codiary.backend.domain.member.dto.response.MemberResponseDTO;
import lombok.RequiredArgsConstructor;
Expand All @@ -30,10 +29,7 @@ public class MemberQueryService{
private final PostRepository postRepository;

public ApiResponse<MemberResponseDTO.MemberImageDTO> getProfileImage(Long memberId) {
Member user = memberRepository.findById(memberId).orElseThrow(() -> new MemberHandler(ErrorStatus.MEMBER_NOT_FOUND));
String url = (user.getImage() != null) ? user.getImage().getImageUrl() : "";
MemberResponseDTO.MemberImageDTO response = new MemberResponseDTO.MemberImageDTO(url);
return ApiResponse.onSuccess(SuccessStatus.MEMBER_OK, response);
return ApiResponse.onSuccess(SuccessStatus.MEMBER_OK, memberRepository.findProfileImageUrl(memberId));
}

public Member getUserProfile(Long memberId) {
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
package com.codiary.backend.domain.techstack.repository;

import com.codiary.backend.domain.member.entity.Member;
import com.codiary.backend.domain.techstack.entity.TechStacks;
import com.codiary.backend.domain.techstack.enumerate.TechStack;
import org.springframework.data.jpa.repository.JpaRepository;

public interface TechStackRepository extends JpaRepository<TechStacks, Long> {
boolean existsByNameAndMember(TechStack name, Member member);
}
Loading