From 81d3005f8f38287577b107dc62a0296e04ae5f42 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=EA=B9=80=EB=B6=80=EA=B2=BD?= Date: Tue, 4 Feb 2025 18:33:15 +0900 Subject: [PATCH 1/4] =?UTF-8?q?[REFACTOR]=20GoogleUserInfoDTO=20=EC=9D=B4?= =?UTF-8?q?=EB=A6=84=20=EB=B3=80=EA=B2=BD=20=EB=B0=8F=20auth=20=EB=8F=84?= =?UTF-8?q?=EB=A9=94=EC=9D=B8=EC=9C=BC=EB=A1=9C=20=EC=9D=B4=EB=8F=99?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Ref: TICO-363, TICO-367 Related to: TICO-378 --- .../dto/GoogleUserInfo.java} | 6 +++--- .../pomoro_do/domain/auth/service/AuthService.java | 4 ++-- .../domain/auth/service/AuthServiceImpl.java | 12 ++++++------ 3 files changed, 11 insertions(+), 11 deletions(-) rename backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/{user/dto/GoogleUserInfoDTO.java => auth/dto/GoogleUserInfo.java} (64%) diff --git a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/dto/GoogleUserInfoDTO.java b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/auth/dto/GoogleUserInfo.java similarity index 64% rename from backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/dto/GoogleUserInfoDTO.java rename to backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/auth/dto/GoogleUserInfo.java index 1b40c273..3dffa15a 100644 --- a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/dto/GoogleUserInfoDTO.java +++ b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/auth/dto/GoogleUserInfo.java @@ -1,10 +1,10 @@ -package com.tico.pomoro_do.domain.user.dto; +package com.tico.pomoro_do.domain.auth.dto; import lombok.Builder; import lombok.Getter; @Getter -public class GoogleUserInfoDTO { +public class GoogleUserInfo { private String userId; private String email; @@ -12,7 +12,7 @@ public class GoogleUserInfoDTO { private String pictureUrl; @Builder - public GoogleUserInfoDTO(String userId, String email, String name, String pictureUrl) { + public GoogleUserInfo(String userId, String email, String name, String pictureUrl) { this.userId = userId; this.email = email; this.name = name; diff --git a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/auth/service/AuthService.java b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/auth/service/AuthService.java index 5e387688..de14265d 100644 --- a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/auth/service/AuthService.java +++ b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/auth/service/AuthService.java @@ -1,7 +1,7 @@ package com.tico.pomoro_do.domain.auth.service; -import com.tico.pomoro_do.domain.user.dto.GoogleUserInfoDTO; +import com.tico.pomoro_do.domain.auth.dto.GoogleUserInfo; import com.tico.pomoro_do.domain.auth.dto.response.TokenResponse; import com.tico.pomoro_do.domain.user.entity.User; import com.tico.pomoro_do.global.enums.ProfileImageType; @@ -23,7 +23,7 @@ public interface AuthService { * @throws IOException IO 예외 * @throws CustomException 구글 ID 토큰이 유효하지 않은 경우 예외 */ - GoogleUserInfoDTO verifyGoogleIdToken(String idToken) throws GeneralSecurityException, IOException, IllegalArgumentException; + GoogleUserInfo verifyGoogleIdToken(String idToken) throws GeneralSecurityException, IOException, IllegalArgumentException; /** * 구글 ID 토큰으로 로그인 처리 diff --git a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/auth/service/AuthServiceImpl.java b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/auth/service/AuthServiceImpl.java index 0d8b671a..84900856 100644 --- a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/auth/service/AuthServiceImpl.java +++ b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/auth/service/AuthServiceImpl.java @@ -8,7 +8,7 @@ import com.tico.pomoro_do.domain.auth.dto.response.TokenResponse; import com.tico.pomoro_do.domain.category.entity.Category; import com.tico.pomoro_do.domain.category.service.CategoryService; -import com.tico.pomoro_do.domain.user.dto.GoogleUserInfoDTO; +import com.tico.pomoro_do.domain.auth.dto.GoogleUserInfo; import com.tico.pomoro_do.domain.user.entity.SocialLogin; import com.tico.pomoro_do.domain.user.entity.User; import com.tico.pomoro_do.domain.user.repository.SocialLoginRepository; @@ -53,7 +53,7 @@ public class AuthServiceImpl implements AuthService { // 구글 ID 토큰 무결성 검사 @Override - public GoogleUserInfoDTO verifyGoogleIdToken(String idToken) throws GeneralSecurityException, IOException, IllegalArgumentException { + public GoogleUserInfo verifyGoogleIdToken(String idToken) throws GeneralSecurityException, IOException, IllegalArgumentException { NetHttpTransport transport = new NetHttpTransport(); JsonFactory jsonFactory = new GsonFactory(); GoogleIdTokenVerifier verifier = new GoogleIdTokenVerifier.Builder(transport, jsonFactory) @@ -63,7 +63,7 @@ public GoogleUserInfoDTO verifyGoogleIdToken(String idToken) throws GeneralSecur GoogleIdToken googleIdToken = verifier.verify(idToken); // 검증 실패시 IllegalArgumentException를 던짐 if (googleIdToken != null) { GoogleIdToken.Payload payload = googleIdToken.getPayload(); - return GoogleUserInfoDTO.builder() + return GoogleUserInfo.builder() .userId(payload.getSubject()) .email(payload.getEmail()) .name((String) payload.get("name")) @@ -84,7 +84,7 @@ public TokenResponse googleLogin(String idTokenHeader, String deviceId) throws G // 토큰 추출 String idToken = jwtUtil.extractToken(idTokenHeader, TokenType.GOOGLE); // 구글 토큰 유효성 검증 - GoogleUserInfoDTO userInfo = verifyGoogleIdToken(idToken); + GoogleUserInfo userInfo = verifyGoogleIdToken(idToken); // 회원 가입 여부 판단 -> 회원 가입 x -> 에러 발생 validateUserExists(userInfo.getEmail()); // 회원 가입되어 있으면 토큰 발급 @@ -102,7 +102,7 @@ public TokenResponse googleJoin(String idTokenHeader, String deviceId, String ni // 구글 idToken 유효성 검사 및 추출 String idToken = jwtUtil.extractToken(idTokenHeader, TokenType.GOOGLE); // 구글 id 토큰 검증 - GoogleUserInfoDTO userInfo = verifyGoogleIdToken(idToken); + GoogleUserInfo userInfo = verifyGoogleIdToken(idToken); // 사용자의 이메일 중복 체크 checkIfUserAlreadyRegistered(userInfo.getEmail()); @@ -172,7 +172,7 @@ private void checkIfUserAlreadyRegistered(String email) { * GOOGLE 유형인 경우 구글 프로필 이미지 URL을 반환하며, * DEFAULT 유형인 경우 null을 반환합니다. */ - private String determineProfileImageUrl(ProfileImageType imageType, MultipartFile profileImage, GoogleUserInfoDTO userInfo) { + private String determineProfileImageUrl(ProfileImageType imageType, MultipartFile profileImage, GoogleUserInfo userInfo) { return switch (imageType) { case FILE -> imageService.imageUpload(profileImage, S3Folder.PROFILES.getFolderName()); case GOOGLE -> userInfo.getPictureUrl(); From d3a7804a55b4759a48db7374936c4183cc74a1b9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=EA=B9=80=EB=B6=80=EA=B2=BD?= Date: Wed, 5 Feb 2025 23:19:03 +0900 Subject: [PATCH 2/4] =?UTF-8?q?[REFACTOR]=20User=20=EC=97=94=ED=8B=B0?= =?UTF-8?q?=ED=8B=B0=20=ED=95=84=EB=93=9C=EB=AA=85=20username=20=E2=86=92?= =?UTF-8?q?=20email=20=EB=B3=80=EA=B2=BD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - username 필드명을 email로 변경하여 의미 명확화 - 인증 및 조회 로직에서 email 사용으로 수정 Resolves: TICO-372 Related to: TICO-378 --- .../domain/auth/service/AuthServiceImpl.java | 10 ++-- .../service/CustomUserDetailsService.java | 4 +- .../controller/CategoryController.java | 24 ++++---- .../category/service/CategoryServiceImpl.java | 18 +++--- .../user/controller/AdminController.java | 16 +++--- .../user/controller/UserController.java | 12 ++-- .../{AdminDTO.java => AdminRequest.java} | 6 +- ...DetailDTO.java => UserDetailResponse.java} | 10 ++-- .../pomoro_do/domain/user/entity/User.java | 21 ++++--- .../user/repository/UserRepository.java | 8 +-- .../domain/user/service/AdminService.java | 6 +- .../domain/user/service/AdminServiceImpl.java | 56 +++++++++---------- .../domain/user/service/FollowService.java | 20 +++---- .../user/service/FollowServiceImpl.java | 40 ++++++------- .../domain/user/service/UserService.java | 10 ++-- .../domain/user/service/UserServiceImpl.java | 30 +++++----- 16 files changed, 147 insertions(+), 144 deletions(-) rename backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/dto/request/{AdminDTO.java => AdminRequest.java} (84%) rename backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/dto/response/{UserDetailDTO.java => UserDetailResponse.java} (73%) diff --git a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/auth/service/AuthServiceImpl.java b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/auth/service/AuthServiceImpl.java index 84900856..75959991 100644 --- a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/auth/service/AuthServiceImpl.java +++ b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/auth/service/AuthServiceImpl.java @@ -144,7 +144,7 @@ private void joinValidateInputs(String deviceId, String nickname) { * @param email 사용자 이메일 */ private void validateUserExists(String email) { - if (!userRepository.existsByUsername(email)) { + if (!userRepository.existsByEmail(email)) { log.error("사용자 등록되지 않음: 이메일 = {}", email); throw new CustomException(ErrorCode.USER_NOT_FOUND); } @@ -156,7 +156,7 @@ private void validateUserExists(String email) { * @param email 사용자의 이메일 */ private void checkIfUserAlreadyRegistered(String email) { - if (userRepository.existsByUsername(email)) { + if (userRepository.existsByEmail(email)) { log.error("이미 등록된 사용자: 이메일 = {}", email); throw new CustomException(ErrorCode.USER_ALREADY_REGISTERED); } @@ -183,17 +183,17 @@ private String determineProfileImageUrl(ProfileImageType imageType, MultipartFil // User 생성 @Override - public User createUser(String username, String nickname, String profileImageUrl, UserRole role) { + public User createUser(String email, String nickname, String profileImageUrl, UserRole role) { User user = User.builder() - .username(username) + .email(email) .nickname(nickname) .profileImageUrl(profileImageUrl) .role(role) .build(); userRepository.save(user); - log.info("사용자 저장 성공: 이메일 = {}", username); + log.info("사용자 저장 성공: 이메일 = {}", email); return user; } diff --git a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/auth/service/CustomUserDetailsService.java b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/auth/service/CustomUserDetailsService.java index 9aa673ad..0e204f34 100644 --- a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/auth/service/CustomUserDetailsService.java +++ b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/auth/service/CustomUserDetailsService.java @@ -28,13 +28,13 @@ public class CustomUserDetailsService implements UserDetailsService { public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException { // DB에서 조회 - Optional userData = userRepository.findByUsername(username); + Optional userData = userRepository.findByEmail(username); // 데이터가 있으면 검증 진행 if (userData.isPresent()) { User user = userData.get(); AuthUser authUser = AuthUser.builder() - .email(user.getUsername()) + .email(user.getEmail()) .role(String.valueOf(user.getRole())) .build(); diff --git a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/category/controller/CategoryController.java b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/category/controller/CategoryController.java index 8f675d5e..b6ee4939 100644 --- a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/category/controller/CategoryController.java +++ b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/category/controller/CategoryController.java @@ -59,8 +59,8 @@ public ResponseEntity> createCategory( @AuthenticationPrincipal CustomUserDetails customUserDetails, @Valid @RequestBody CategoryCreationDTO request ){ - String username = customUserDetails.getUsername(); - categoryService.createCategory(username, request); + String email = customUserDetails.getUsername(); + categoryService.createCategory(email, request); SuccessResponseDTO successResponse = SuccessResponseDTO.builder() .status(SuccessCode.CATEGORY_CREATION_SUCCESS.getHttpStatus().value()) @@ -82,8 +82,8 @@ public ResponseEntity> createCategory( public ResponseEntity> getCategories( @AuthenticationPrincipal CustomUserDetails customUserDetails ) { - String username = customUserDetails.getUsername(); - CategoryDTO categoryDTO = categoryService.getCategories(username); + String email = customUserDetails.getUsername(); + CategoryDTO categoryDTO = categoryService.getCategories(email); SuccessResponseDTO successResponse = SuccessResponseDTO.builder() .status(SuccessCode.CATEGORY_FETCH_SUCCESS.getHttpStatus().value()) @@ -102,8 +102,8 @@ public ResponseEntity> getCategories( public ResponseEntity>> getGeneralCategories( @AuthenticationPrincipal CustomUserDetails customUserDetails ) { - String username = customUserDetails.getUsername(); - User user = userService.findByUsername(username); + String email = customUserDetails.getUsername(); + User user = userService.findByEmail(email); List categories = categoryService.getGeneralCategories(user); SuccessResponseDTO> successResponse = SuccessResponseDTO.>builder() @@ -123,8 +123,8 @@ public ResponseEntity>> getGeneralCa public ResponseEntity>> getGroupCategories( @AuthenticationPrincipal CustomUserDetails customUserDetails ) { - String username = customUserDetails.getUsername(); - User user = userService.findByUsername(username); + String email = customUserDetails.getUsername(); + User user = userService.findByEmail(email); List categories = categoryService.getGroupCategories(user); SuccessResponseDTO> successResponse = SuccessResponseDTO.>builder() @@ -144,8 +144,8 @@ public ResponseEntity>> getGroupCatego public ResponseEntity>> getInvitedGroupCategories( @AuthenticationPrincipal CustomUserDetails customUserDetails ) { - String username = customUserDetails.getUsername(); - User user = userService.findByUsername(username); + String email = customUserDetails.getUsername(); + User user = userService.findByEmail(email); List groupCategories = categoryService.getInvitedGroupCategories(user); SuccessResponseDTO> successResponse = SuccessResponseDTO.>builder() @@ -166,8 +166,8 @@ public ResponseEntity> getCategoryDetail( @PathVariable Long categoryId, @AuthenticationPrincipal CustomUserDetails customUserDetails ) { - String username = customUserDetails.getUsername(); - CategoryDetailDTO categoryDetailDTO = categoryService.getCategoryDetail(categoryId, username); + String email = customUserDetails.getUsername(); + CategoryDetailDTO categoryDetailDTO = categoryService.getCategoryDetail(categoryId, email); SuccessResponseDTO successResponse = SuccessResponseDTO.builder() .status(SuccessCode.CATEGORY_DETAIL_FETCH_SUCCESS.getHttpStatus().value()) diff --git a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/category/service/CategoryServiceImpl.java b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/category/service/CategoryServiceImpl.java index 363fe509..07b32324 100644 --- a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/category/service/CategoryServiceImpl.java +++ b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/category/service/CategoryServiceImpl.java @@ -40,14 +40,14 @@ public class CategoryServiceImpl implements CategoryService { /** * 카테고리 생성 * - * @param hostName 카테고리를 생성하는 호스트 유저의 이름 + * @param hostEmail 카테고리를 생성하는 호스트 유저의 이메일 * @param categoryCreationDTO 생성할 카테고리의 정보가 담긴 DTO */ @Override @Transactional - public void createCategory(String hostName, CategoryCreationDTO categoryCreationDTO){ + public void createCategory(String hostEmail, CategoryCreationDTO categoryCreationDTO){ - User host = userService.findByUsername(hostName); + User host = userService.findByEmail(hostEmail); // 일반/그룹 카테고리 생성 Category category = createNewCategory( @@ -139,13 +139,13 @@ public void createGroupMember(Category category, User member, GroupInvitationSta /** * 주어진 사용자 이름을 기반으로 사용자의 일반, 그룹, 초대받은 카테고리를 조회 * - * @param username 사용자의 이름 + * @param email 사용자의 이메일 * @return 사용자에 해당하는 일반 카테고리, 그룹 카테고리, 초대받은 그룹 카테고리를 포함하는 CategoryDTO 객체 */ @Override - public CategoryDTO getCategories(String username) { + public CategoryDTO getCategories(String email) { // 사용자 조회 - User user = userService.findByUsername(username); + User user = userService.findByEmail(email); // 일반 카테고리 List generalCategories = getGeneralCategories(user); @@ -250,11 +250,11 @@ private Map calculateMemberCounts(List groupCategories * 카테고리 상세 조회 * * @param categoryId 카테고리 ID - * @param username 조회한 유저 이메일 + * @param email 조회한 유저 이메일 * @return CategoryDetailDTO 객체 */ @Override - public CategoryDetailDTO getCategoryDetail(Long categoryId, String username){ + public CategoryDetailDTO getCategoryDetail(Long categoryId, String email){ Category category = findByCategoryId(categoryId); List groupMemberDTOList = new ArrayList<>(); // 그룹 멤버 조회 @@ -277,7 +277,7 @@ public CategoryDetailDTO getCategoryDetail(Long categoryId, String username){ .categoryId(categoryId) .title(category.getTitle()) .hostNickname(category.getHost().getNickname()) - .hostStatus(category.getHost().getUsername().equals(username)) + .hostStatus(category.getHost().getEmail().equals(email)) .type(category.getType()) .visibility(category.getVisibility()) .members(groupMemberDTOList) diff --git a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/controller/AdminController.java b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/controller/AdminController.java index 6ae527ce..196b49e6 100644 --- a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/controller/AdminController.java +++ b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/controller/AdminController.java @@ -1,7 +1,7 @@ package com.tico.pomoro_do.domain.user.controller; import com.tico.pomoro_do.domain.auth.dto.response.TokenResponse; -import com.tico.pomoro_do.domain.user.dto.request.AdminDTO; +import com.tico.pomoro_do.domain.user.dto.request.AdminRequest; import com.tico.pomoro_do.domain.user.service.AdminService; import com.tico.pomoro_do.global.code.SuccessCode; import com.tico.pomoro_do.global.response.SuccessResponseDTO; @@ -33,7 +33,7 @@ public class AdminController { /** * 관리자 회원가입 API * - * @param adminDTO AdminDTO 객체 + * @param adminRequest AdminDTO 객체 * @param profileImage 관리자 프로필 이미지 파일 * @return 성공 시 TokenDTO를 포함하는 SuccessResponseDTO */ @@ -50,17 +50,17 @@ public class AdminController { }) @PostMapping(consumes = MediaType.MULTIPART_FORM_DATA_VALUE) public ResponseEntity> adminJoin( - @Valid @RequestPart AdminDTO adminDTO, + @Valid @RequestPart AdminRequest adminRequest, @RequestPart(value = "profileImage", required = false) MultipartFile profileImage ) { - TokenResponse jwtResponse = adminService.adminJoin(adminDTO, profileImage); + TokenResponse jwtResponse = adminService.adminJoin(adminRequest, profileImage); SuccessResponseDTO successResponse = SuccessResponseDTO.builder() .status(SuccessCode.ADMIN_SIGNUP_SUCCESS.getHttpStatus().value()) .message(SuccessCode.ADMIN_SIGNUP_SUCCESS.getMessage()) .data(jwtResponse) .build(); - log.info("관리자 회원가입 성공: {}", adminDTO.getUsername()); + log.info("관리자 회원가입 성공: {}", adminRequest.getEmail()); return ResponseEntity.status(HttpStatus.CREATED).body(successResponse); } @@ -83,16 +83,16 @@ public ResponseEntity> adminJoin( }) @PostMapping("/login") public ResponseEntity> adminLogin( - @Valid @RequestBody AdminDTO request + @Valid @RequestBody AdminRequest request ) { - log.info("관리자 로그인 요청: {}", request.getUsername()); + log.info("관리자 로그인 요청: {}", request.getEmail()); TokenResponse jwtResponse = adminService.adminLogin(request); SuccessResponseDTO successResponse = SuccessResponseDTO.builder() .status(SuccessCode.ADMIN_LOGIN_SUCCESS.getHttpStatus().value()) .message(SuccessCode.ADMIN_LOGIN_SUCCESS.getMessage()) .data(jwtResponse) .build(); - log.info("관리자 로그인 성공: {}", request.getUsername()); + log.info("관리자 로그인 성공: {}", request.getEmail()); return ResponseEntity.ok(successResponse); } } diff --git a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/controller/UserController.java b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/controller/UserController.java index 25640d5b..e5683ded 100644 --- a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/controller/UserController.java +++ b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/controller/UserController.java @@ -1,7 +1,7 @@ package com.tico.pomoro_do.domain.user.controller; import com.tico.pomoro_do.domain.user.dto.response.FollowResponse; -import com.tico.pomoro_do.domain.user.dto.response.UserDetailDTO; +import com.tico.pomoro_do.domain.user.dto.response.UserDetailResponse; import com.tico.pomoro_do.domain.user.service.UserService; import com.tico.pomoro_do.domain.auth.security.CustomUserDetails; import com.tico.pomoro_do.global.code.SuccessCode; @@ -31,12 +31,12 @@ public class UserController { */ @Operation(summary = "현재 사용자 정보 조회", description = "인증된 사용자의 상세 정보를 조회합니다.") @GetMapping("/me") - public ResponseEntity> getMyDetail( + public ResponseEntity> getMyDetail( @AuthenticationPrincipal CustomUserDetails customUserDetails ) { - UserDetailDTO userDetailResponse = userService.getMyDetail(customUserDetails.getUsername()); - SuccessResponseDTO successResponse = SuccessResponseDTO.builder() + UserDetailResponse userDetailResponse = userService.getMyDetail(customUserDetails.getUsername()); + SuccessResponseDTO successResponse = SuccessResponseDTO.builder() .status(SuccessCode.USER_FETCH_SUCCESS.getHttpStatus().value()) .message(SuccessCode.USER_FETCH_SUCCESS.getMessage()) .data(userDetailResponse) @@ -58,8 +58,8 @@ public ResponseEntity> getUserDetail( @AuthenticationPrincipal CustomUserDetails customUserDetails, @PathVariable Long userId ) { - String username = customUserDetails.getUsername(); - FollowResponse response = userService.getUserDetail(username, userId); + String email = customUserDetails.getUsername(); + FollowResponse response = userService.getUserDetail(email, userId); SuccessResponseDTO successResponse = SuccessResponseDTO.builder() .status(SuccessCode.USER_FETCH_SUCCESS.getHttpStatus().value()) .message(SuccessCode.USER_FETCH_SUCCESS.getMessage()) diff --git a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/dto/request/AdminDTO.java b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/dto/request/AdminRequest.java similarity index 84% rename from backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/dto/request/AdminDTO.java rename to backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/dto/request/AdminRequest.java index 569114ce..7ccf075d 100644 --- a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/dto/request/AdminDTO.java +++ b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/dto/request/AdminRequest.java @@ -8,12 +8,12 @@ @Getter @Schema(description = "Admin Info") -public class AdminDTO { +public class AdminRequest { @Email @NotBlank(message = "이메일을 입력해주세요.") - @Schema(description = "아이디", example = "chadoll@pomorodo.shop") - private String username; + @Schema(description = "이메일", example = "chadoll@pomorodo.shop") + private String email; @Size(max = 10, message = "닉네임은 최대 10자까지 가능합니다.") @NotBlank(message = "닉네임을 입력해주세요.") diff --git a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/dto/response/UserDetailDTO.java b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/dto/response/UserDetailResponse.java similarity index 73% rename from backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/dto/response/UserDetailDTO.java rename to backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/dto/response/UserDetailResponse.java index ea91a117..00018f43 100644 --- a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/dto/response/UserDetailDTO.java +++ b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/dto/response/UserDetailResponse.java @@ -5,12 +5,12 @@ import lombok.Getter; @Getter -public class UserDetailDTO { +public class UserDetailResponse { private final Long userId; @Schema(description = "이메일 주소", example = "example@example.com") - private final String username; + private final String email; private final String nickname; @@ -23,10 +23,10 @@ public class UserDetailDTO { private final int followerCount; @Builder - public UserDetailDTO(Long userId, String username, String nickname, String profileImageUrl, - int followingCount, int followerCount) { + public UserDetailResponse(Long userId, String email, String nickname, String profileImageUrl, + int followingCount, int followerCount) { this.userId = userId; - this.username = username; + this.email = email; this.nickname = nickname; this.profileImageUrl = profileImageUrl; this.followingCount = followingCount; diff --git a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/entity/User.java b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/entity/User.java index 14215b52..51e36276 100644 --- a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/entity/User.java +++ b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/entity/User.java @@ -21,7 +21,7 @@ public class User extends BaseTimeEntity { private Long id; @Column(nullable = false, unique = true) - private String username; // email + private String email; @Column(nullable = false, length = 10) private String nickname; @@ -39,8 +39,8 @@ public class User extends BaseTimeEntity { private UserStatus status = UserStatus.ACTIVE; @Builder - public User(String username, String nickname, String profileImageUrl, UserRole role) { - this.username = username; + public User(String email, String nickname, String profileImageUrl, UserRole role) { + this.email = email; this.nickname = nickname; this.profileImageUrl = profileImageUrl; this.role = role; @@ -53,13 +53,16 @@ public void updateNickname(String nickname) { public void updateProfileImageUrl(String profileImageUrl) { this.profileImageUrl = profileImageUrl; } +// +// public void updateRole(UserRole role) { +// this.role = role; +// } - public void updateRole(UserRole role) { - this.role = role; - } +// public void updateStatus(UserStatus status) { +// this.status = status; +// } - public void updateStatus(UserStatus status) { - this.status = status; + public void deactivate() { + this.status = UserStatus.DEACTIVATED; } - } \ No newline at end of file diff --git a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/repository/UserRepository.java b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/repository/UserRepository.java index d60d3c72..f12c8957 100644 --- a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/repository/UserRepository.java +++ b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/repository/UserRepository.java @@ -7,13 +7,13 @@ public interface UserRepository extends JpaRepository { - //username을 받아 DB 테이블에서 회원을 조회하는 메소드 작성 - Optional findByUsername(String username); + //email을 받아 DB 테이블에서 회원을 조회하는 메소드 작성 + Optional findByEmail(String email); Optional findById(Long userId); - boolean existsByUsername(String username); + boolean existsByEmail(String email); - void deleteByUsername(String username); + void deleteByEmail(String email); } diff --git a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/AdminService.java b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/AdminService.java index 732cef05..17b121c4 100644 --- a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/AdminService.java +++ b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/AdminService.java @@ -1,14 +1,14 @@ package com.tico.pomoro_do.domain.user.service; import com.tico.pomoro_do.domain.auth.dto.response.TokenResponse; -import com.tico.pomoro_do.domain.user.dto.request.AdminDTO; +import com.tico.pomoro_do.domain.user.dto.request.AdminRequest; import org.springframework.web.multipart.MultipartFile; public interface AdminService { // 관리자 회원가입 - TokenResponse adminJoin(AdminDTO adminDTO, MultipartFile profileImage); + TokenResponse adminJoin(AdminRequest adminRequest, MultipartFile profileImage); // 관리자 로그인 - TokenResponse adminLogin(AdminDTO adminDTO); + TokenResponse adminLogin(AdminRequest adminRequest); } diff --git a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/AdminServiceImpl.java b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/AdminServiceImpl.java index 7cf87f4f..bf2ebcdb 100644 --- a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/AdminServiceImpl.java +++ b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/AdminServiceImpl.java @@ -3,7 +3,7 @@ import com.tico.pomoro_do.domain.auth.dto.response.TokenResponse; import com.tico.pomoro_do.domain.auth.service.AuthService; import com.tico.pomoro_do.domain.auth.service.TokenService; -import com.tico.pomoro_do.domain.user.dto.request.AdminDTO; +import com.tico.pomoro_do.domain.user.dto.request.AdminRequest; import com.tico.pomoro_do.domain.user.entity.User; import com.tico.pomoro_do.domain.user.repository.UserRepository; import com.tico.pomoro_do.global.code.ErrorCode; @@ -35,23 +35,23 @@ public class AdminServiceImpl implements AdminService { /** * 관리자 회원가입 처리 * - * @param adminDTO AdminDTO 객체 + * @param adminRequest AdminRequest 객체 * @param profileImage 프로필 이미지 * @return 성공 시 새 Access, Refresh 토큰을 포함하는 TokenDTO * @throws CustomException 이메일 도메인이 유효하지 않거나 이미 등록된 사용자인 경우 예외를 던집니다. */ @Override @Transactional - public TokenResponse adminJoin(AdminDTO adminDTO, MultipartFile profileImage) { - String username = adminDTO.getUsername(); - String nickname = adminDTO.getNickname(); + public TokenResponse adminJoin(AdminRequest adminRequest, MultipartFile profileImage) { + String email = adminRequest.getEmail(); + String nickname = adminRequest.getNickname(); // 관리자 회원가입 도메인 가져오기 - String domain = getEmailDomain(username); + String domain = getEmailDomain(email); // 관리자 회원가입 이메일 도메인 검증 validateAdminEmailDomain(domain); // 관리자 이메일 가입 여부 검증 - checkUserExistence(username); + checkUserExistence(email); // profileImage URL 가져오기 String profileImageUrl; @@ -62,40 +62,40 @@ public TokenResponse adminJoin(AdminDTO adminDTO, MultipartFile profileImage) { } // 관리자 생성하기 - User admin = authService.createUser(username, nickname, profileImageUrl, UserRole.ADMIN); + User admin = authService.createUser(email, nickname, profileImageUrl, UserRole.ADMIN); // 역할 String role = String.valueOf(UserRole.ADMIN); // 관리자 고유 번호: UUID 기반 + 역할명 - String deviceId = UUID.nameUUIDFromBytes(username.getBytes()).toString() + "_" + role; + String deviceId = UUID.nameUUIDFromBytes(email.getBytes()).toString() + "_" + role; - return tokenService.createAuthTokens(username, String.valueOf(UserRole.ADMIN), deviceId); + return tokenService.createAuthTokens(email, String.valueOf(UserRole.ADMIN), deviceId); } /** * 관리자 로그인 처리 * - * @param adminDTO AdminDTO 객체 + * @param adminRequest AdminRequest 객체 * @return 성공 시 새 Access, Refresh 토큰을 포함하는 TokenDTO * @throws CustomException 이메일 도메인이 유효하지 않거나 관리자가 아닌 경우 예외를 던집니다. */ @Override @Transactional - public TokenResponse adminLogin(AdminDTO adminDTO){ - String username = adminDTO.getUsername(); - String nickname = adminDTO.getNickname(); + public TokenResponse adminLogin(AdminRequest adminRequest){ + String email = adminRequest.getEmail(); + String nickname = adminRequest.getNickname(); // 로그인 도메인 가져오기 - String domain = getEmailDomain(username); + String domain = getEmailDomain(email); // 로그인 이메일 검증 (관리자 도메인) validateAdminEmailDomain(domain); // 관리자 로그인 검증 - validateAdminUser(username, nickname); + validateAdminUser(email, nickname); // 역할 String role = String.valueOf(UserRole.ADMIN); // 관리자 고유 번호: UUID 기반 + 역할명 - String deviceId = UUID.nameUUIDFromBytes(username.getBytes()).toString() + "_" + role; - return tokenService.createAuthTokens(username, role, deviceId); + String deviceId = UUID.nameUUIDFromBytes(email.getBytes()).toString() + "_" + role; + return tokenService.createAuthTokens(email, role, deviceId); } /** @@ -124,12 +124,12 @@ private void validateAdminEmailDomain(String domain) { /** * 사용자가 이미 존재하는지 확인 * - * @param username 사용자 이름 + * @param email 사용자 이메일 * @throws CustomException 이미 등록된 사용자인 경우 예외 발생 */ - private void checkUserExistence(String username) { - if (userRepository.existsByUsername(username)) { - log.error("이미 등록된 사용자: {}", username); + private void checkUserExistence(String email) { + if (userRepository.existsByEmail(email)) { + log.error("이미 등록된 사용자: {}", email); throw new CustomException(ErrorCode.USER_ALREADY_REGISTERED); } } @@ -137,23 +137,23 @@ private void checkUserExistence(String username) { /** * 관리자 검증 * - * @param username 사용자 이름 + * @param email 사용자 이메일 * @param nickname 사용자 닉네임 * @throws CustomException 사용자가 존재하지 않거나 관리자가 아닌 경우 예외 발생 */ - private void validateAdminUser(String username, String nickname) { - Optional userData = userRepository.findByUsername(username); + private void validateAdminUser(String email, String nickname) { + Optional userData = userRepository.findByEmail(email); if (userData.isEmpty()) { - log.error("사용자를 찾을 수 없음: {}", username); + log.error("사용자를 찾을 수 없음: {}", email); throw new CustomException(ErrorCode.USER_NOT_FOUND); } User admin = userData.get(); if (!admin.getRole().equals(UserRole.ADMIN)) { - log.error("관리자 권한 없음: {}", username); + log.error("관리자 권한 없음: {}", email); throw new CustomException(ErrorCode.NOT_AN_ADMIN); } if (!admin.getNickname().equals(nickname)) { - log.error("닉네임 불일치: {}", username); + log.error("닉네임 불일치: {}", email); throw new CustomException(ErrorCode.ADMIN_LOGIN_FAILED); } } diff --git a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/FollowService.java b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/FollowService.java index 5ef50abb..66d43a25 100644 --- a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/FollowService.java +++ b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/FollowService.java @@ -9,40 +9,40 @@ public interface FollowService { /** * 특정 사용자 팔로우 * - * @param followerUsername 팔로우하는 사용자 이름 + * @param followerUserEmail 팔로우하는 사용자 이메일 * @param followingId 팔로우될 사용자 ID */ - void follow(String followerUsername, Long followingId); + void follow(String followerUserEmail, Long followingId); /** * 특정 사용자 팔로우 취소 * - * @param followerUsername 현재 사용자 이름 + * @param followerUserEmail 현재 사용자 이메일 * @param followingId 팔로우 취소하는 사용자 ID */ - void unfollow(String followerUsername, Long followingId); + void unfollow(String followerUserEmail, Long followingId); /** * 사용자를 팔로우 중인 사용자 목록을 조회 * - * @param username 현재 인증된 사용자의 사용자 이름 + * @param email 현재 인증된 사용자 이메일 * @return FollowResponse 객체 리스트 반환 */ - List getFollowers(String username); + List getFollowers(String email); /** * 사용자가 팔로우 중인 사용자 목록을 조회 * - * @param username 현재 인증된 사용자의 사용자 이름 + * @param email 현재 인증된 사용자 이메일 * @return FollowResponse 객체 리스트 반환 */ - List getFollowings(String username); + List getFollowings(String email); /** * 특정 사용자가 타겟 사용자를 팔로우하고 있는지 여부 * - * @param currentUserId 현재 인증된 사용자의 ID - * @param targetUserId 팔로우 여부를 확인할 대상 사용자의 ID + * @param currentUserId 현재 인증된 사용자 ID + * @param targetUserId 팔로우 여부를 확인할 대상의 사용자 ID * @return 팔로우 여부 반환 */ boolean isFollowing(Long currentUserId, Long targetUserId); diff --git a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/FollowServiceImpl.java b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/FollowServiceImpl.java index 06c3cf65..7cc98985 100644 --- a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/FollowServiceImpl.java +++ b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/FollowServiceImpl.java @@ -28,22 +28,22 @@ public class FollowServiceImpl implements FollowService { // 특정 사용자를 팔로우 @Override @Transactional - public void follow(String followerUsername, Long followingId) { + public void follow(String followerUserEmail, Long followingId) { // 유효성 검사 (null 또는 음수 체크) ValidationUtils.validateUserId(followingId); - User follower = userService.findByUsername(followerUsername); + User follower = userService.findByEmail(followerUserEmail); User following = userService.findByUserId(followingId); // 본인을 팔로우 하는 지 확인 if (follower.equals(following)) { - log.warn("사용자 '{}'가 본인을 팔로우하려고 시도했습니다.", followerUsername); + log.warn("사용자 '{}'가 본인을 팔로우하려고 시도했습니다.", followerUserEmail); throw new CustomException(ErrorCode.SELF_FOLLOW_NOT_ALLOWED); } // 이미 팔로우 중인지 확인 if (isFollowing(follower.getId(), followingId)) { - log.warn("사용자 '{}'가 이미 사용자 ID '{}'를 팔로우했습니다.", followerUsername, followingId); + log.warn("사용자 '{}'가 이미 사용자 ID '{}'를 팔로우했습니다.", followerUserEmail, followingId); throw new CustomException(ErrorCode.ALREADY_FOLLOWED); } @@ -58,12 +58,12 @@ public void follow(String followerUsername, Long followingId) { // 언팔로우 @Override @Transactional - public void unfollow(String followerUsername, Long followingId) { + public void unfollow(String followerUserEmail, Long followingId) { // 유효성 검사 (null 또는 음수 체크) ValidationUtils.validateUserId(followingId); // 팔로워 유저 조회 - User follower = userService.findByUsername(followerUsername); + User follower = userService.findByEmail(followerUserEmail); // 팔로이 유저 조회 User following = userService.findByUserId(followingId); @@ -76,28 +76,28 @@ public void unfollow(String followerUsername, Long followingId) { // 나를 팔로우하고 있는 사용자 목록을 조회 @Override - public List getFollowers(String username) { + public List getFollowers(String email) { // 사용자를 팔로우하는 사용자 목록을 조회 - return getFollowList(username, false); + return getFollowList(email, false); } // 내가 팔로우하고 있는 사용자 목록을 조회 @Override - public List getFollowings(String username) { + public List getFollowings(String email) { // 팔로우 중인 사용자 목록을 조회 - return getFollowList(username, true); + return getFollowList(email, true); } /** - * 팔로우 목록 또는 팔로워 목록을 조회하고 DTO 리스트로 변환하는 메서드 + * 팔로우 목록 또는 팔로워 목록을 조회하고 FollowResponse 리스트로 변환하는 메서드 * - * @param username 현재 인증된 사용자의 사용자 이름 + * @param email 현재 인증된 사용자 이메일 * @param isFollowings 팔로잉 목록인지 여부 (true: 팔로잉 목록, false: 팔로워 목록) - * @return FollowUserDTO 객체 리스트 반환 + * @return FollowResponse 객체 리스트 반환 */ - private List getFollowList(String username, boolean isFollowings) { + private List getFollowList(String email, boolean isFollowings) { // 사용자 정보 조회 - User user = userService.findByUsername(username); + User user = userService.findByEmail(email); // 팔로우 목록 또는 팔로워 목록을 조회 List followList = isFollowings @@ -112,12 +112,12 @@ private List getFollowList(String username, boolean isFollowings } /** - * Follow 엔티티를 FollowUserDTO로 변환하는 메서드 + * Follow 엔티티를 FollowResponse로 변환하는 메서드 * * @param follow Follow 엔티티 * @param isFollowings 팔로우 목록인지 여부 - * @param currentUserId 현재 인증된 사용자의 ID - * @return FollowUserDTO 객체 반환 + * @param currentUserId 현재 인증된 사용자 ID + * @return FollowResponse 객체 반환 */ private FollowResponse convertToFollowResponse(Follow follow, boolean isFollowings, Long currentUserId) { // 타겟 유저를 결정: 팔로우 목록일 경우 수신자, 팔로워 목록일 경우 발신자 @@ -144,8 +144,8 @@ public boolean isFollowing(Long userId, Long targetId) { /** * 팔로우 관계를 조회하고 없을 경우 예외를 발생시킵니다. * - * @param followerId 팔로우 요청자의 ID - * @param followingId 팔로우 대상자의 ID + * @param followerId 팔로우 요청자 ID + * @param followingId 팔로우 대상자 ID * @return Follow 객체 */ private Follow getFollowRelationship(Long followerId, Long followingId) { diff --git a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/UserService.java b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/UserService.java index fa03b716..e6e6ca3a 100644 --- a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/UserService.java +++ b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/UserService.java @@ -1,24 +1,24 @@ package com.tico.pomoro_do.domain.user.service; import com.tico.pomoro_do.domain.user.dto.response.FollowResponse; -import com.tico.pomoro_do.domain.user.dto.response.UserDetailDTO; +import com.tico.pomoro_do.domain.user.dto.response.UserDetailResponse; import com.tico.pomoro_do.domain.user.entity.User; public interface UserService { // 내 정보 조회 - UserDetailDTO getMyDetail(String username); + UserDetailResponse getMyDetail(String email); // 유저 이름으로 조회 - User findByUsername(String username); + User findByEmail(String email); // 유저 아이디로 조회 User findByUserId(Long userId); // 특정 유저 조회 - FollowResponse getUserDetail(String username, Long userId); + FollowResponse getUserDetail(String email, Long userId); // 유저 삭제 - void deleteUser(String username, String deviceId, String refreshHeader); + void deleteUser(String email, String deviceId, String refreshHeader); } diff --git a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/UserServiceImpl.java b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/UserServiceImpl.java index 498701db..d97fc248 100644 --- a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/UserServiceImpl.java +++ b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/UserServiceImpl.java @@ -2,7 +2,7 @@ import com.tico.pomoro_do.domain.auth.service.TokenService; import com.tico.pomoro_do.domain.user.dto.response.FollowResponse; -import com.tico.pomoro_do.domain.user.dto.response.UserDetailDTO; +import com.tico.pomoro_do.domain.user.dto.response.UserDetailResponse; import com.tico.pomoro_do.domain.user.entity.User; import com.tico.pomoro_do.domain.user.repository.FollowRepository; import com.tico.pomoro_do.domain.user.repository.UserRepository; @@ -24,17 +24,17 @@ public class UserServiceImpl implements UserService{ final private TokenService tokenService; @Override - public UserDetailDTO getMyDetail(String username) { - User user = findByUsername(username); + public UserDetailResponse getMyDetail(String email) { + User user = findByEmail(email); // 내가 팔로우하는 사람의 수 계산 int followingCount = followRepository.countByFollower(user); // 나를 팔로우하는 사람의 수 계산 int followerCount = followRepository.countByFollowing(user); - return UserDetailDTO.builder() + return UserDetailResponse.builder() .userId(user.getId()) - .username(user.getUsername()) + .email(user.getEmail()) .nickname(user.getNickname()) .profileImageUrl(user.getProfileImageUrl()) .followingCount(followingCount) @@ -43,10 +43,10 @@ public UserDetailDTO getMyDetail(String username) { } @Override - public FollowResponse getUserDetail(String username, Long userId) { + public FollowResponse getUserDetail(String email, Long userId) { - // 주어진 username에 해당하는 현재 사용자 ID 조회 - Long myUserId = findByUsername(username).getId(); + // 주어진 email에 해당하는 현재 사용자 ID 조회 + Long myUserId = findByEmail(email).getId(); // 주어진 userId에 해당하는 특정 사용자 정보 조회 User user = findByUserId(userId); @@ -64,20 +64,20 @@ public FollowResponse getUserDetail(String username, Long userId) { @Override @Transactional - public void deleteUser(String username, String deviceId, String refreshHeader) { + public void deleteUser(String email, String deviceId, String refreshHeader) { // 회원 토큰 검증 - tokenService.validateRefreshTokenDetails(refreshHeader, deviceId, username); + tokenService.validateRefreshTokenDetails(refreshHeader, deviceId, email); // 해당 회원의 모든 리프레시 토큰 삭제 - tokenService.deleteAllRefreshTokensByEmail(username); + tokenService.deleteAllRefreshTokensByEmail(email); // 해당 유저 삭제 - userRepository.deleteByUsername(username); + userRepository.deleteByEmail(email); } @Override - public User findByUsername(String username) { - return userRepository.findByUsername(username) + public User findByEmail(String email) { + return userRepository.findByEmail(email) .orElseThrow(() -> { - log.error("사용자를 찾을 수 없음: {}", username); + log.error("사용자를 찾을 수 없음: {}", email); return new CustomException(ErrorCode.USER_NOT_FOUND); }); } From fba2c316da1762baa60055c3d6d956678f95049e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=EA=B9=80=EB=B6=80=EA=B2=BD?= Date: Thu, 6 Feb 2025 15:56:26 +0900 Subject: [PATCH 3/4] =?UTF-8?q?[REFACTOR]=20ImageDTO=20=E2=86=92=20ImageRe?= =?UTF-8?q?sponse=EB=A1=9C=20=EC=9D=B4=EB=A6=84=20=EB=B3=80=EA=B2=BD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Related to: TICO-372, TICO-378 --- .../domain/user/controller/ImageController.java | 10 +++++----- .../dto/response/{ImageDTO.java => ImageResponse.java} | 4 ++-- 2 files changed, 7 insertions(+), 7 deletions(-) rename backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/dto/response/{ImageDTO.java => ImageResponse.java} (84%) diff --git a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/controller/ImageController.java b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/controller/ImageController.java index 72653051..3445818e 100644 --- a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/controller/ImageController.java +++ b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/controller/ImageController.java @@ -1,6 +1,6 @@ package com.tico.pomoro_do.domain.user.controller; -import com.tico.pomoro_do.domain.user.dto.response.ImageDTO; +import com.tico.pomoro_do.domain.user.dto.response.ImageResponse; import com.tico.pomoro_do.domain.user.service.ImageService; import com.tico.pomoro_do.global.code.SuccessCode; import com.tico.pomoro_do.global.enums.S3Folder; @@ -45,20 +45,20 @@ public class ImageController { @ApiResponse(responseCode = "400", description = "유효하지 않은 이미지 파일"), }) @PostMapping(consumes = MediaType.MULTIPART_FORM_DATA_VALUE) - public ResponseEntity> imageUpload( + public ResponseEntity> imageUpload( @RequestParam("image") MultipartFile image ) { String imageUrl = imageService.imageUpload(image, S3Folder.IMAGES.getFolderName()); - ImageDTO imageDTO = ImageDTO.builder() + ImageResponse imageResponse = ImageResponse.builder() .imageUrl(imageUrl) .build(); - SuccessResponseDTO response = SuccessResponseDTO.builder() + SuccessResponseDTO response = SuccessResponseDTO.builder() .status(SuccessCode.IMAGE_UPLOAD_SUCCESS.getHttpStatus().value()) .message(SuccessCode.IMAGE_UPLOAD_SUCCESS.getMessage()) - .data(imageDTO) + .data(imageResponse) .build(); return ResponseEntity.ok(response); diff --git a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/dto/response/ImageDTO.java b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/dto/response/ImageResponse.java similarity index 84% rename from backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/dto/response/ImageDTO.java rename to backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/dto/response/ImageResponse.java index 0ddaa423..52c907bc 100644 --- a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/dto/response/ImageDTO.java +++ b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/dto/response/ImageResponse.java @@ -7,13 +7,13 @@ @Getter @Schema(description = "Image Response") -public class ImageDTO { +public class ImageResponse { @Schema(description = "이미지 URL", example = "https://s3.amazonaws.com/foldername/bucketname/uuid.jpg") private final String imageUrl; @Builder - public ImageDTO(String imageUrl){ + public ImageResponse(String imageUrl){ this.imageUrl = imageUrl; } } \ No newline at end of file From cfe145652552a08869bc5a8fcf7421df810ca3a5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=EA=B9=80=EB=B6=80=EA=B2=BD?= Date: Thu, 6 Feb 2025 16:37:33 +0900 Subject: [PATCH 4/4] =?UTF-8?q?[REFACTOR]=20AuthService=20=EC=A4=91?= =?UTF-8?q?=EB=B3=B5=20=ED=95=A8=EC=88=98=20=EC=A0=9C=EA=B1=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Related to: TICO-372, TICO-378 --- .../domain/auth/service/AuthServiceImpl.java | 30 ++----------- .../pomoro_do/domain/user/entity/User.java | 2 +- .../domain/user/service/AdminService.java | 18 +++++++- .../domain/user/service/AdminServiceImpl.java | 42 +++--------------- .../domain/user/service/UserService.java | 28 +++++++++--- .../domain/user/service/UserServiceImpl.java | 43 +++++++++++++------ 6 files changed, 79 insertions(+), 84 deletions(-) diff --git a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/auth/service/AuthServiceImpl.java b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/auth/service/AuthServiceImpl.java index 75959991..db74caad 100644 --- a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/auth/service/AuthServiceImpl.java +++ b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/auth/service/AuthServiceImpl.java @@ -14,6 +14,7 @@ import com.tico.pomoro_do.domain.user.repository.SocialLoginRepository; import com.tico.pomoro_do.domain.user.repository.UserRepository; import com.tico.pomoro_do.domain.user.service.ImageService; +import com.tico.pomoro_do.domain.user.service.UserService; import com.tico.pomoro_do.global.auth.jwt.JWTUtil; import com.tico.pomoro_do.global.code.ErrorCode; import com.tico.pomoro_do.global.common.constants.CategoryConstants; @@ -46,6 +47,7 @@ public class AuthServiceImpl implements AuthService { private final JWTUtil jwtUtil; private final UserRepository userRepository; private final SocialLoginRepository socialLoginRepository; + private final UserService userService; private final TokenService tokenService; private final ImageService imageService; private final CategoryService categoryService; @@ -86,7 +88,7 @@ public TokenResponse googleLogin(String idTokenHeader, String deviceId) throws G // 구글 토큰 유효성 검증 GoogleUserInfo userInfo = verifyGoogleIdToken(idToken); // 회원 가입 여부 판단 -> 회원 가입 x -> 에러 발생 - validateUserExists(userInfo.getEmail()); + userService.validateEmailExists(userInfo.getEmail()); // 회원 가입되어 있으면 토큰 발급 return tokenService.createAuthTokens(userInfo.getEmail(), String.valueOf(UserRole.USER), deviceId); } @@ -104,7 +106,7 @@ public TokenResponse googleJoin(String idTokenHeader, String deviceId, String ni // 구글 id 토큰 검증 GoogleUserInfo userInfo = verifyGoogleIdToken(idToken); // 사용자의 이메일 중복 체크 - checkIfUserAlreadyRegistered(userInfo.getEmail()); + userService.isEmailRegistered(userInfo.getEmail()); // 알맞는 profileImage url 가져오기 (null 가능) String profileImageUrl = determineProfileImageUrl(imageType, profileImage, userInfo); @@ -138,30 +140,6 @@ private void joinValidateInputs(String deviceId, String nickname) { ValidationUtils.validateNickname(nickname); } - /** - * 사용자 등록 여부 확인 메서드 - * - * @param email 사용자 이메일 - */ - private void validateUserExists(String email) { - if (!userRepository.existsByEmail(email)) { - log.error("사용자 등록되지 않음: 이메일 = {}", email); - throw new CustomException(ErrorCode.USER_NOT_FOUND); - } - } - - /** - * 사용자가 이미 등록되어 있는지 확인합니다. - * - * @param email 사용자의 이메일 - */ - private void checkIfUserAlreadyRegistered(String email) { - if (userRepository.existsByEmail(email)) { - log.error("이미 등록된 사용자: 이메일 = {}", email); - throw new CustomException(ErrorCode.USER_ALREADY_REGISTERED); - } - } - /** * 프로필 이미지 URL을 결정합니다. * diff --git a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/entity/User.java b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/entity/User.java index 51e36276..53140d05 100644 --- a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/entity/User.java +++ b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/entity/User.java @@ -21,7 +21,7 @@ public class User extends BaseTimeEntity { private Long id; @Column(nullable = false, unique = true) - private String email; + private String email; // 소셜 로그인 제공자의 이메일 @Column(nullable = false, length = 10) private String nickname; diff --git a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/AdminService.java b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/AdminService.java index 17b121c4..d204a0af 100644 --- a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/AdminService.java +++ b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/AdminService.java @@ -2,13 +2,27 @@ import com.tico.pomoro_do.domain.auth.dto.response.TokenResponse; import com.tico.pomoro_do.domain.user.dto.request.AdminRequest; +import com.tico.pomoro_do.global.exception.CustomException; import org.springframework.web.multipart.MultipartFile; public interface AdminService { - // 관리자 회원가입 + /** + * 관리자 회원가입 + * + * @param adminRequest AdminRequest 객체 + * @param profileImage 프로필 이미지 + * @return 성공 시 새 Access, Refresh 토큰을 포함하는 TokenResponse + * @throws CustomException 이메일 도메인이 유효하지 않거나 이미 등록된 사용자인 경우 예외를 던집니다. + */ TokenResponse adminJoin(AdminRequest adminRequest, MultipartFile profileImage); - // 관리자 로그인 + /** + * 관리자 로그인 + * + * @param adminRequest AdminRequest 객체 + * @return 성공 시 새 Access, Refresh 토큰을 포함하는 TokenResponse + * @throws CustomException 이메일 도메인이 유효하지 않거나 관리자가 아닌 경우 예외를 던집니다. + */ TokenResponse adminLogin(AdminRequest adminRequest); } diff --git a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/AdminServiceImpl.java b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/AdminServiceImpl.java index bf2ebcdb..7780dba1 100644 --- a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/AdminServiceImpl.java +++ b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/AdminServiceImpl.java @@ -25,21 +25,14 @@ @Slf4j public class AdminServiceImpl implements AdminService { - private final UserRepository userRepository; + private final UserService userService; private final AuthService authService; private final TokenService tokenService; private final ImageService imageService; private static final String ADMIN_EMAIL_DOMAIN = "pomorodo.shop"; - /** - * 관리자 회원가입 처리 - * - * @param adminRequest AdminRequest 객체 - * @param profileImage 프로필 이미지 - * @return 성공 시 새 Access, Refresh 토큰을 포함하는 TokenDTO - * @throws CustomException 이메일 도메인이 유효하지 않거나 이미 등록된 사용자인 경우 예외를 던집니다. - */ + // 관리자 회원가입 @Override @Transactional public TokenResponse adminJoin(AdminRequest adminRequest, MultipartFile profileImage) { @@ -51,7 +44,7 @@ public TokenResponse adminJoin(AdminRequest adminRequest, MultipartFile profileI // 관리자 회원가입 이메일 도메인 검증 validateAdminEmailDomain(domain); // 관리자 이메일 가입 여부 검증 - checkUserExistence(email); + userService.isEmailRegistered(email); // profileImage URL 가져오기 String profileImageUrl; @@ -72,13 +65,7 @@ public TokenResponse adminJoin(AdminRequest adminRequest, MultipartFile profileI return tokenService.createAuthTokens(email, String.valueOf(UserRole.ADMIN), deviceId); } - /** - * 관리자 로그인 처리 - * - * @param adminRequest AdminRequest 객체 - * @return 성공 시 새 Access, Refresh 토큰을 포함하는 TokenDTO - * @throws CustomException 이메일 도메인이 유효하지 않거나 관리자가 아닌 경우 예외를 던집니다. - */ + // 관리자 로그인 @Override @Transactional public TokenResponse adminLogin(AdminRequest adminRequest){ @@ -121,19 +108,6 @@ private void validateAdminEmailDomain(String domain) { } } - /** - * 사용자가 이미 존재하는지 확인 - * - * @param email 사용자 이메일 - * @throws CustomException 이미 등록된 사용자인 경우 예외 발생 - */ - private void checkUserExistence(String email) { - if (userRepository.existsByEmail(email)) { - log.error("이미 등록된 사용자: {}", email); - throw new CustomException(ErrorCode.USER_ALREADY_REGISTERED); - } - } - /** * 관리자 검증 * @@ -142,12 +116,8 @@ private void checkUserExistence(String email) { * @throws CustomException 사용자가 존재하지 않거나 관리자가 아닌 경우 예외 발생 */ private void validateAdminUser(String email, String nickname) { - Optional userData = userRepository.findByEmail(email); - if (userData.isEmpty()) { - log.error("사용자를 찾을 수 없음: {}", email); - throw new CustomException(ErrorCode.USER_NOT_FOUND); - } - User admin = userData.get(); + User admin = userService.findByEmail(email); + if (!admin.getRole().equals(UserRole.ADMIN)) { log.error("관리자 권한 없음: {}", email); throw new CustomException(ErrorCode.NOT_AN_ADMIN); diff --git a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/UserService.java b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/UserService.java index e6e6ca3a..c2d81201 100644 --- a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/UserService.java +++ b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/UserService.java @@ -3,22 +3,38 @@ import com.tico.pomoro_do.domain.user.dto.response.FollowResponse; import com.tico.pomoro_do.domain.user.dto.response.UserDetailResponse; import com.tico.pomoro_do.domain.user.entity.User; +import com.tico.pomoro_do.global.exception.CustomException; public interface UserService { - // 내 정보 조회 - UserDetailResponse getMyDetail(String email); + // 사용자 아이디로 조회 + User findByUserId(Long userId); - // 유저 이름으로 조회 + // 사용자 이메일로 조회 User findByEmail(String email); - // 유저 아이디로 조회 - User findByUserId(Long userId); + // 내 정보 조회 + UserDetailResponse getMyDetail(String email); - // 특정 유저 조회 + // 특정 사용자 정보 조회 FollowResponse getUserDetail(String email, Long userId); // 유저 삭제 void deleteUser(String email, String deviceId, String refreshHeader); + /** + * 이메일을 통해 사용자가 이미 등록되어 있는지 확인 + * + * @param email 사용자 이메일 + * @throws CustomException 이미 등록된 사용자인 경우 예외를 던짐 + */ + void isEmailRegistered(String email); + + /** + * 이메일을 통해 사용자가 등록되어 있는지 검증 + * + * @param email 사용자 이메일 + * @throws CustomException 등록되지 않은 사용자일 경우 예외를 던짐 + */ + void validateEmailExists(String email); } diff --git a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/UserServiceImpl.java b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/UserServiceImpl.java index d97fc248..2df83537 100644 --- a/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/UserServiceImpl.java +++ b/backend/pomoro-do/src/main/java/com/tico/pomoro_do/domain/user/service/UserServiceImpl.java @@ -23,6 +23,24 @@ public class UserServiceImpl implements UserService{ final private FollowRepository followRepository; final private TokenService tokenService; + @Override + public User findByUserId(Long userId) { + return userRepository.findById(userId) + .orElseThrow(() -> { + log.error("사용자를 찾을 수 없음: {}", userId); + return new CustomException(ErrorCode.USER_NOT_FOUND); + }); + } + + @Override + public User findByEmail(String email) { + return userRepository.findByEmail(email) + .orElseThrow(() -> { + log.error("사용자를 찾을 수 없음: {}", email); + return new CustomException(ErrorCode.USER_NOT_FOUND); + }); + } + @Override public UserDetailResponse getMyDetail(String email) { User user = findByEmail(email); @@ -73,22 +91,21 @@ public void deleteUser(String email, String deviceId, String refreshHeader) { userRepository.deleteByEmail(email); } + // 이메일이 등록되어 있는 지 검증 @Override - public User findByEmail(String email) { - return userRepository.findByEmail(email) - .orElseThrow(() -> { - log.error("사용자를 찾을 수 없음: {}", email); - return new CustomException(ErrorCode.USER_NOT_FOUND); - }); + public void isEmailRegistered(String email) { + if (userRepository.existsByEmail(email)) { + log.error("이미 등록된 사용자: {}", email); + throw new CustomException(ErrorCode.USER_ALREADY_REGISTERED); + } } + // 이메일이 사용 가능한 지 검증 @Override - public User findByUserId(Long userId) { - return userRepository.findById(userId) - .orElseThrow(() -> { - log.error("사용자를 찾을 수 없음: {}", userId); - return new CustomException(ErrorCode.USER_NOT_FOUND); - }); + public void validateEmailExists(String email) { + if (!userRepository.existsByEmail(email)) { + log.error("등록되지 않은 사용자: 이메일 = {}", email); + throw new CustomException(ErrorCode.USER_NOT_FOUND); + } } - }