diff --git a/src/main/java/com/helpmeCookies/global/ApiResponse/ApiResponse.java b/src/main/java/com/helpmeCookies/global/ApiResponse/ApiResponse.java new file mode 100644 index 0000000..269f39a --- /dev/null +++ b/src/main/java/com/helpmeCookies/global/ApiResponse/ApiResponse.java @@ -0,0 +1,29 @@ +package com.helpmeCookies.global.ApiResponse; + +import jakarta.annotation.Nullable; +import lombok.AllArgsConstructor; +import lombok.Getter; +import lombok.RequiredArgsConstructor; +import org.springframework.http.HttpStatus; + +@Getter +@AllArgsConstructor +@RequiredArgsConstructor +public class ApiResponse { + + private final int code; + private final String message; + private T data; + + public static ApiResponse success(SuccessCode successCode, T data) { + return new ApiResponse(successCode.getCode(), successCode.getMessage(),data); + } + + public static ApiResponse success(SuccessCode successCode) { + return new ApiResponse<>(successCode.getCode(), successCode.getMessage(),null); + } + + public static ApiResponse error(HttpStatus errorCode, String message) { + return new ApiResponse<>(errorCode.value(), message,null); + } +} diff --git a/src/main/java/com/helpmeCookies/global/ApiResponse/SuccessCode.java b/src/main/java/com/helpmeCookies/global/ApiResponse/SuccessCode.java new file mode 100644 index 0000000..13ee8a4 --- /dev/null +++ b/src/main/java/com/helpmeCookies/global/ApiResponse/SuccessCode.java @@ -0,0 +1,16 @@ +package com.helpmeCookies.global.ApiResponse; + +import lombok.AllArgsConstructor; +import lombok.Getter; +import org.springframework.http.HttpStatus; + +@AllArgsConstructor +@Getter +public enum SuccessCode { + OK(200, "OK"), + CREATED_SUCCESS(201, "저장에 성공했습니다"); + + private final int code; + private final String message; + +} diff --git a/src/main/java/com/helpmeCookies/global/config/ProPertyConfig.java b/src/main/java/com/helpmeCookies/global/config/ProPertyConfig.java new file mode 100644 index 0000000..338afd7 --- /dev/null +++ b/src/main/java/com/helpmeCookies/global/config/ProPertyConfig.java @@ -0,0 +1,12 @@ +package com.helpmeCookies.global.config; + +import org.springframework.boot.context.properties.ConfigurationPropertiesScan; +import org.springframework.boot.context.properties.EnableConfigurationProperties; +import org.springframework.context.annotation.Configuration; + +import com.helpmeCookies.global.jwt.JwtProperties; + +@Configuration +@EnableConfigurationProperties(JwtProperties.class) +public class ProPertyConfig { +} diff --git a/src/main/java/com/helpmeCookies/global/exception/GlobalExceptionHandler.java b/src/main/java/com/helpmeCookies/global/exception/GlobalExceptionHandler.java index ad5237a..9705e08 100644 --- a/src/main/java/com/helpmeCookies/global/exception/GlobalExceptionHandler.java +++ b/src/main/java/com/helpmeCookies/global/exception/GlobalExceptionHandler.java @@ -1,5 +1,8 @@ package com.helpmeCookies.global.exception; +import com.helpmeCookies.global.ApiResponse.ApiResponse; +import org.springframework.http.HttpStatus; +import org.springframework.http.ResponseEntity; import org.springframework.web.bind.annotation.ControllerAdvice; import org.springframework.web.bind.annotation.ExceptionHandler; @@ -10,8 +13,8 @@ public class GlobalExceptionHandler { @ExceptionHandler(ResourceNotFoundException.class) - public String handleResourceNotFoundException() { - return "해당 리소스를 찾을 수 없습니다."; + public ResponseEntity> handleResourceNotFoundException() { + return ResponseEntity.badRequest().body(ApiResponse.error(HttpStatus.BAD_REQUEST,"해당 리소스를 찾을 수 없습니다.")); } @ExceptionHandler(DuplicateRequestException.class) diff --git a/src/main/java/com/helpmeCookies/global/jwt/JwtProperties.java b/src/main/java/com/helpmeCookies/global/jwt/JwtProperties.java new file mode 100644 index 0000000..b99dd2f --- /dev/null +++ b/src/main/java/com/helpmeCookies/global/jwt/JwtProperties.java @@ -0,0 +1,20 @@ +package com.helpmeCookies.global.jwt; + +import org.springframework.boot.context.properties.ConfigurationProperties; +import org.springframework.stereotype.Component; + +import lombok.Getter; +import lombok.Setter; + +@Component +@ConfigurationProperties(prefix = "jwt") +@Getter +@Setter +public class JwtProperties { + private String secret; + private long accessTokenExpireTime; + private long refreshTokenExpireTime; + + public JwtProperties() { + } +} diff --git a/src/main/java/com/helpmeCookies/global/jwt/JwtProvider.java b/src/main/java/com/helpmeCookies/global/jwt/JwtProvider.java index 6eb0844..dcafdff 100644 --- a/src/main/java/com/helpmeCookies/global/jwt/JwtProvider.java +++ b/src/main/java/com/helpmeCookies/global/jwt/JwtProvider.java @@ -12,12 +12,13 @@ import io.jsonwebtoken.Claims; import io.jsonwebtoken.Jwts; import io.jsonwebtoken.SignatureAlgorithm; +import lombok.RequiredArgsConstructor; @Component +@RequiredArgsConstructor public class JwtProvider implements InitializingBean { - private String secret = "4099a46b-39db-4860-a61b-2ae76ea24c43"; - private long accessTokenExpireTime = 1800000; // 30 minutes; - private long refreshTokenExpireTime = 259200000; // 3 days; + + private final JwtProperties jwtProperties; private Key secretKey; private static final String ROLE = "role"; private static final String IS_ACCESS_TOKEN = "isAccessToken"; @@ -92,7 +93,7 @@ private JwtUser claimsToJwtUser(Claims claims) { } private String generateToken(JwtUser jwtUser, boolean isAccessToken) { - long expireTime = isAccessToken ? accessTokenExpireTime : refreshTokenExpireTime; + long expireTime = isAccessToken ? jwtProperties.getAccessTokenExpireTime() : jwtProperties.getRefreshTokenExpireTime(); Date expireDate = new Date(System.currentTimeMillis() + expireTime); return Jwts.builder() .signWith(secretKey) @@ -112,6 +113,6 @@ private Claims extractClaims(String rawToken) { @Override public void afterPropertiesSet() { - secretKey = new SecretKeySpec(secret.getBytes(), SignatureAlgorithm.HS256.getJcaName()); + secretKey = new SecretKeySpec(jwtProperties.getSecret().getBytes(), SignatureAlgorithm.HS256.getJcaName()); } } diff --git a/src/main/java/com/helpmeCookies/global/security/JwtAuthenticationFilter.java b/src/main/java/com/helpmeCookies/global/security/JwtAuthenticationFilter.java index 4570b65..0b996a2 100644 --- a/src/main/java/com/helpmeCookies/global/security/JwtAuthenticationFilter.java +++ b/src/main/java/com/helpmeCookies/global/security/JwtAuthenticationFilter.java @@ -24,7 +24,6 @@ @Component public class JwtAuthenticationFilter extends OncePerRequestFilter { private final JwtProvider jwtProvider; - private static final String AUTHORIZATION_HEADER = "Authorization"; @Override @@ -46,6 +45,9 @@ protected void doFilterInternal(HttpServletRequest request, HttpServletResponse Authentication authentication = new UsernamePasswordAuthenticationToken(jwtUser, null, jwtUser.getAuthorities()); SecurityContextHolder.getContext().setAuthentication(authentication); + } else { + log.info("유효하지 않은 토큰 발생"); + response.sendError(HttpServletResponse.SC_UNAUTHORIZED, "토큰이 유효하지 않습니다."); } filterChain.doFilter(request, response); diff --git a/src/main/java/com/helpmeCookies/global/security/WebSecurityConfig.java b/src/main/java/com/helpmeCookies/global/security/WebSecurityConfig.java index d84cc09..57cf551 100644 --- a/src/main/java/com/helpmeCookies/global/security/WebSecurityConfig.java +++ b/src/main/java/com/helpmeCookies/global/security/WebSecurityConfig.java @@ -74,7 +74,9 @@ public SecurityFilterChain filterChain(HttpSecurity http) throws Exception { "/actuator/**", "/v1/**", "swagger-ui/**", - "/test/signup" + "/test/signup", + "/v1/artist", + "/v1/artists" ).permitAll() .anyRequest().authenticated() ).exceptionHandling((exception) -> exception diff --git a/src/main/java/com/helpmeCookies/product/controller/ProductController.java b/src/main/java/com/helpmeCookies/product/controller/ProductController.java index e9617e6..2bbcad6 100644 --- a/src/main/java/com/helpmeCookies/product/controller/ProductController.java +++ b/src/main/java/com/helpmeCookies/product/controller/ProductController.java @@ -1,5 +1,7 @@ package com.helpmeCookies.product.controller; +import com.helpmeCookies.global.ApiResponse.ApiResponse; +import com.helpmeCookies.global.ApiResponse.SuccessCode; import com.helpmeCookies.product.dto.ImageUpload; import static com.helpmeCookies.product.util.SortUtil.convertProductSort; @@ -29,6 +31,11 @@ public class ProductController implements ProductApiDocs { private final ProductService productService; private final ProductImageService productImageService; + @PostMapping("/successTest") + public ResponseEntity> saveTest() { + return ResponseEntity.ok(ApiResponse.success(SuccessCode.OK)); + } + @PostMapping public ResponseEntity saveProduct(@RequestBody ProductRequest productRequest) { Product product = productService.save(productRequest); diff --git a/src/main/java/com/helpmeCookies/user/controller/ArtistController.java b/src/main/java/com/helpmeCookies/user/controller/ArtistController.java index 4b00d3b..f9530ff 100644 --- a/src/main/java/com/helpmeCookies/user/controller/ArtistController.java +++ b/src/main/java/com/helpmeCookies/user/controller/ArtistController.java @@ -1,5 +1,7 @@ package com.helpmeCookies.user.controller; +import com.helpmeCookies.global.ApiResponse.ApiResponse; +import com.helpmeCookies.global.ApiResponse.SuccessCode; import com.helpmeCookies.global.jwt.JwtUser; import com.helpmeCookies.user.controller.apiDocs.ArtistApiDocs; import com.helpmeCookies.user.dto.ArtistInfoPage; @@ -7,8 +9,6 @@ import com.helpmeCookies.user.dto.request.StudentArtistReq; import com.helpmeCookies.user.dto.response.ArtistDetailsRes; import com.helpmeCookies.user.service.ArtistService; -import io.swagger.v3.oas.annotations.Operation; -import io.swagger.v3.oas.annotations.tags.Tag; import lombok.RequiredArgsConstructor; import org.springframework.data.domain.PageRequest; import org.springframework.http.ResponseEntity; @@ -26,44 +26,47 @@ public class ArtistController implements ArtistApiDocs { private final ArtistService artistService; @PostMapping("/v1/artists/students") - public ResponseEntity registerStudents( + public ResponseEntity> registerStudents( @RequestBody StudentArtistReq artistDetailsReq, @AuthenticationPrincipal JwtUser jwtUser ) { artistService.registerStudentsArtist(artistDetailsReq, jwtUser.getId()); - return ResponseEntity.ok().build(); + return ResponseEntity.ok((ApiResponse.success(SuccessCode.OK))); } @PostMapping("/v1/artists/bussinesses") - public ResponseEntity registerbussinsess( + public ResponseEntity> registerbussinsess( @RequestBody BusinessArtistReq businessArtistReq, @AuthenticationPrincipal JwtUser jwtUser ) { artistService.registerBusinessArtist(businessArtistReq, jwtUser.getId()); - return ResponseEntity.ok().build(); + return ResponseEntity.ok((ApiResponse.success(SuccessCode.OK))); } @GetMapping("/v1/artists/{userId}") - public ArtistDetailsRes getArtist( + public ResponseEntity> getArtist( @PathVariable Long userId ) { - return artistService.getArtistDetails(userId); + ArtistDetailsRes artistDetailsRes = artistService.getArtistDetails(userId); + return ResponseEntity.ok((ApiResponse.success(SuccessCode.OK, artistDetailsRes))); } @GetMapping("/v1/artist") - public ArtistDetailsRes getArtist( + public ResponseEntity> getArtist( @AuthenticationPrincipal JwtUser jwtUser ) { - return artistService.getArtistDetails(jwtUser.getId()); + ArtistDetailsRes artistDetailsRes = artistService.getArtistDetails(jwtUser.getId()); + return ResponseEntity.ok((ApiResponse.success(SuccessCode.OK, artistDetailsRes))); } @GetMapping("/v1/artists") - public ResponseEntity getArtistsByPage( + public ResponseEntity> getArtistsByPage( @RequestParam("query") String query, @RequestParam(name = "size", required = false, defaultValue = "20") int size, @RequestParam("page") int page ) { var pageable = PageRequest.of(page, size); - return ResponseEntity.ok(artistService.getArtistsByPage(query, pageable)); + ArtistInfoPage.Paging artistInfoPage = artistService.getArtistsByPage(query, pageable); + return ResponseEntity.ok((ApiResponse.success(SuccessCode.OK, artistInfoPage))); } } diff --git a/src/main/java/com/helpmeCookies/user/controller/LoginController.java b/src/main/java/com/helpmeCookies/user/controller/LoginController.java index 71e4391..03431cf 100644 --- a/src/main/java/com/helpmeCookies/user/controller/LoginController.java +++ b/src/main/java/com/helpmeCookies/user/controller/LoginController.java @@ -55,7 +55,7 @@ public JwtToken signup() { } @GetMapping("/oauth2/login/kakao") - public JwtToken ttt(@AuthenticationPrincipal OAuth2User oAuth2User) { + public JwtToken loginKakao(@AuthenticationPrincipal OAuth2User oAuth2User) { KakaoOAuth2Response kakaoUser = KakaoOAuth2Response.from(oAuth2User.getAttributes()); return jwtProvider.createToken(userDetailsService.loadUserByEmail(kakaoUser.email(), kakaoUser.nickname())); } diff --git a/src/main/java/com/helpmeCookies/user/controller/UserController.java b/src/main/java/com/helpmeCookies/user/controller/UserController.java index 945471d..f7d0874 100644 --- a/src/main/java/com/helpmeCookies/user/controller/UserController.java +++ b/src/main/java/com/helpmeCookies/user/controller/UserController.java @@ -1,9 +1,13 @@ package com.helpmeCookies.user.controller; +import java.io.IOException; +import java.util.List; + import org.springframework.data.domain.Page; import org.springframework.data.domain.Pageable; import org.springframework.data.domain.Sort; import org.springframework.data.web.PageableDefault; +import org.springframework.http.HttpStatus; import org.springframework.http.ResponseEntity; import org.springframework.security.core.annotation.AuthenticationPrincipal; import org.springframework.web.bind.annotation.DeleteMapping; @@ -13,14 +17,19 @@ import org.springframework.web.bind.annotation.PutMapping; import org.springframework.web.bind.annotation.RequestBody; import org.springframework.web.bind.annotation.RestController; +import org.springframework.web.multipart.MultipartFile; +import com.helpmeCookies.global.ApiResponse.ApiResponse; +import com.helpmeCookies.global.ApiResponse.SuccessCode; import com.helpmeCookies.global.jwt.JwtUser; import com.helpmeCookies.user.controller.apiDocs.UserApiDocs; +import com.helpmeCookies.user.dto.UserDto; import com.helpmeCookies.user.dto.response.UserCommonInfoRes; import com.helpmeCookies.user.dto.request.UserReq; import com.helpmeCookies.user.dto.response.UserDetailsInfoRes; import com.helpmeCookies.user.dto.UserTypeDto; import com.helpmeCookies.user.dto.response.UserFollowingRes; +import com.helpmeCookies.user.dto.response.UserImageResponse; import com.helpmeCookies.user.service.UserService; import lombok.RequiredArgsConstructor; @@ -32,60 +41,65 @@ public class UserController implements UserApiDocs { @GetMapping("/v1/users") - public ResponseEntity getUsers( + public ResponseEntity> getUsers( @AuthenticationPrincipal JwtUser jwtUser ) { - return ResponseEntity.ok(UserCommonInfoRes.fromDto(userService.getUserInfo(jwtUser.getId()))); + UserCommonInfoRes userCommonInfoRes = UserCommonInfoRes.fromDto(userService.getUserInfo(jwtUser.getId())); + return ResponseEntity.ok(ApiResponse.success(SuccessCode.OK, userCommonInfoRes)); } @GetMapping("/v1/users/details") - public ResponseEntity getUserDetails( + public ResponseEntity> getUserDetails( @AuthenticationPrincipal JwtUser jwtUser ) { - return ResponseEntity.ok(UserDetailsInfoRes.fromDto(userService.getUserInfo(jwtUser.getId()))); + UserDetailsInfoRes userDetailsInfoRes = UserDetailsInfoRes.fromDto(userService.getUserInfo(jwtUser.getId())); + + return ResponseEntity.ok(ApiResponse.success(SuccessCode.OK, userDetailsInfoRes)); } @GetMapping("/v1/users/type") - public ResponseEntity getUserType( + public ResponseEntity> getUserType( @AuthenticationPrincipal JwtUser jwtUser ) { - return ResponseEntity.ok(userService.getUserType(jwtUser.getId())); + UserTypeDto userTypeDto = userService.getUserType(jwtUser.getId()); + return ResponseEntity.ok(ApiResponse.success(SuccessCode.OK, userTypeDto)); } @PutMapping("/v1/users") - public String updateUser( + public ResponseEntity> updateUser( @AuthenticationPrincipal JwtUser jwtUser, @RequestBody UserReq userReq ) { // UserInfoDto를 통해서 유저 정보를 수정한다. - userService.updateUser(userReq, jwtUser.getId()); - return "ok"; + UserDto userDto = userService.updateUser(userReq.toUserCommonInfoDto(), userReq.toUserInfoDto(), jwtUser.getId()); + return ResponseEntity.ok(ApiResponse.success(SuccessCode.OK, userDto)); } @PostMapping("/v1/users/following/{artistId}") - public ResponseEntity followArtist( + public ResponseEntity> followArtist( @AuthenticationPrincipal JwtUser jwtUser, @PathVariable Long artistId ) { userService.followArtist(jwtUser.getId(), artistId); - return ResponseEntity.ok().build(); + return ResponseEntity.ok(ApiResponse.success(SuccessCode.OK)); } @DeleteMapping("/v1/users/following/{artistId}") - public ResponseEntity unfollowArtist( + public ResponseEntity> unfollowArtist( @AuthenticationPrincipal JwtUser jwtUser, @PathVariable Long artistId ) { userService.unfollowArtist(jwtUser.getId(), artistId); - return ResponseEntity.ok().build(); + return ResponseEntity.ok(ApiResponse.success(SuccessCode.OK)); } @GetMapping("/v1/users/following") - public ResponseEntity> getFollowingList( + public ResponseEntity>> getFollowingList( @AuthenticationPrincipal JwtUser jwtUser, @PageableDefault(size = 10, sort = "createdAt", direction = Sort.Direction.DESC) Pageable pageable ) { - return ResponseEntity.ok(userService.getFollowingWithPaging(jwtUser.getId(), pageable)); + Page followingList = userService.getFollowingWithPaging(jwtUser.getId(), pageable); + return ResponseEntity.ok(ApiResponse.success(SuccessCode.OK, followingList)); } @DeleteMapping("/v1/users") diff --git a/src/main/java/com/helpmeCookies/user/controller/apiDocs/ArtistApiDocs.java b/src/main/java/com/helpmeCookies/user/controller/apiDocs/ArtistApiDocs.java index 4df8e2d..95c6ea8 100644 --- a/src/main/java/com/helpmeCookies/user/controller/apiDocs/ArtistApiDocs.java +++ b/src/main/java/com/helpmeCookies/user/controller/apiDocs/ArtistApiDocs.java @@ -1,6 +1,8 @@ package com.helpmeCookies.user.controller.apiDocs; +import com.helpmeCookies.global.ApiResponse.ApiResponse; import com.helpmeCookies.global.jwt.JwtUser; +import com.helpmeCookies.user.dto.ArtistInfoPage; import com.helpmeCookies.user.dto.ArtistInfoPage.Paging; import com.helpmeCookies.user.dto.request.BusinessArtistReq; import com.helpmeCookies.user.dto.request.StudentArtistReq; @@ -20,32 +22,32 @@ public interface ArtistApiDocs { @Operation(summary = "학생 작가 등록", description = "학생 작가 등록") @PostMapping("/v1/artists/students") - ResponseEntity registerStudents( + ResponseEntity> registerStudents( @RequestBody StudentArtistReq artistDetailsReq, @AuthenticationPrincipal JwtUser jwtUser ); @Operation(summary = "사업자 작가 등록", description = "사업자 작가 등록") @PostMapping("/v1/artists/bussinesses") - ResponseEntity registerbussinsess( + ResponseEntity> registerbussinsess( @RequestBody BusinessArtistReq businessArtistReq, @AuthenticationPrincipal JwtUser jwtUser ); @Operation(summary = "작가 프로필 조회", description = "작가 프로필 조회") @GetMapping("/v1/artists/{userId}") - ArtistDetailsRes getArtist( + ResponseEntity> getArtist( @PathVariable Long userId ); @Operation(summary = "작가 자신의 프로필 조회", description = "작가 자신의 프로필 조회") @GetMapping("/v1/artist") - ArtistDetailsRes getArtist( + ResponseEntity> getArtist( @AuthenticationPrincipal JwtUser jwtUser ); @Operation(summary = "작가 검색") - ResponseEntity getArtistsByPage( + ResponseEntity> getArtistsByPage( String query, @Parameter(description = "default value 20") int size, int page diff --git a/src/main/java/com/helpmeCookies/user/controller/apiDocs/UserApiDocs.java b/src/main/java/com/helpmeCookies/user/controller/apiDocs/UserApiDocs.java index 1eaff9c..06987f7 100644 --- a/src/main/java/com/helpmeCookies/user/controller/apiDocs/UserApiDocs.java +++ b/src/main/java/com/helpmeCookies/user/controller/apiDocs/UserApiDocs.java @@ -11,7 +11,9 @@ import org.springframework.web.bind.annotation.PathVariable; import org.springframework.web.bind.annotation.PostMapping; +import com.helpmeCookies.global.ApiResponse.ApiResponse; import com.helpmeCookies.global.jwt.JwtUser; +import com.helpmeCookies.user.dto.UserDto; import com.helpmeCookies.user.dto.UserTypeDto; import com.helpmeCookies.user.dto.response.UserCommonInfoRes; import com.helpmeCookies.user.dto.response.UserDetailsInfoRes; @@ -25,32 +27,32 @@ public interface UserApiDocs { @Operation(summary = "유저 일반 정보 조회", description = "로그인한 유저의 username, imageUrl, hashtag를 조회한다.") @GetMapping("/v1/users") - ResponseEntity getUsers(@AuthenticationPrincipal JwtUser jwtUser); + ResponseEntity> getUsers(@AuthenticationPrincipal JwtUser jwtUser); @Operation(summary = "유저 상세 정보 조회", description = "로그인한 유저의 상세 정보를 조회한다. 유저의 모든 정보를 조회 할 수 있다.") @GetMapping("/v1/users/details") - ResponseEntity getUserDetails(@AuthenticationPrincipal JwtUser jwtUser); + ResponseEntity> getUserDetails(@AuthenticationPrincipal JwtUser jwtUser); @Operation(summary = "유저 타입 조회", description = "로그인한 유저의 타입과 권한을 조회한다.") @GetMapping("/v1/users/type") - public ResponseEntity getUserType(@AuthenticationPrincipal JwtUser jwtUser); + ResponseEntity> getUserType(@AuthenticationPrincipal JwtUser jwtUser); @Operation(summary = "아티스트 팔로우하기", description = "로그인한 유저가 특정 아티스트를 팔로우한다.") @PostMapping("/v1/users/following/{artistId}") - public ResponseEntity followArtist( + ResponseEntity> followArtist( @AuthenticationPrincipal JwtUser jwtUser, @PathVariable Long artistId ); @Operation(summary = "아티스트 팔로우 취소하기", description = "로그인한 유저가 특정 아티스트를 팔로우 취소한다.") @DeleteMapping("/v1/users/following/{artistId}") - public ResponseEntity unfollowArtist( + ResponseEntity> unfollowArtist( @AuthenticationPrincipal JwtUser jwtUser, @PathVariable Long artistId ); @Operation(summary = "팔로잉 목록 조회", description = "로그인한 유저의 팔로우한 아티스트 목록을 조회한다.") @GetMapping("/v1/users/following") - public ResponseEntity> getFollowingList( + ResponseEntity>> getFollowingList( @AuthenticationPrincipal JwtUser jwtUser, @PageableDefault(size = 10, sort = "createdAt", direction = Sort.Direction.DESC) Pageable pageable ); diff --git a/src/main/java/com/helpmeCookies/user/dto/ArtistInfoDto.java b/src/main/java/com/helpmeCookies/user/dto/ArtistInfoDto.java index 4c50e5e..3d2084e 100644 --- a/src/main/java/com/helpmeCookies/user/dto/ArtistInfoDto.java +++ b/src/main/java/com/helpmeCookies/user/dto/ArtistInfoDto.java @@ -13,7 +13,8 @@ public record ArtistInfoDto( String nickname, Long totalFollowers, Long totalLikes, - String about + String about, + String artistImageUrl ) { public static ArtistInfoDto fromEntity(ArtistInfo artistInfo) { return ArtistInfoDto.builder() @@ -24,6 +25,7 @@ public static ArtistInfoDto fromEntity(ArtistInfo artistInfo) { .totalFollowers(artistInfo.getTotalFollowers()) .totalLikes(artistInfo.getTotalLikes()) .about(artistInfo.getAbout()) + .artistImageUrl(artistInfo.getArtistImageUrl()) .build(); } } diff --git a/src/main/java/com/helpmeCookies/user/dto/UserCommonInfoDto.java b/src/main/java/com/helpmeCookies/user/dto/UserCommonInfoDto.java new file mode 100644 index 0000000..36f61e7 --- /dev/null +++ b/src/main/java/com/helpmeCookies/user/dto/UserCommonInfoDto.java @@ -0,0 +1,7 @@ +package com.helpmeCookies.user.dto; + +public record UserCommonInfoDto( + String nickname, + String ImageUrl +) { +} diff --git a/src/main/java/com/helpmeCookies/user/dto/UserDto.java b/src/main/java/com/helpmeCookies/user/dto/UserDto.java index b3c46e2..05e1de2 100644 --- a/src/main/java/com/helpmeCookies/user/dto/UserDto.java +++ b/src/main/java/com/helpmeCookies/user/dto/UserDto.java @@ -19,7 +19,7 @@ public static UserDto fromEntity(User user) { UserInfoDto.fromEntity(user.getUserInfo()), user.getUserImageUrl(), user.getNickname(), - user.getCreatedAt() + user.getCreatedDate() ); } } diff --git a/src/main/java/com/helpmeCookies/user/dto/request/UserReq.java b/src/main/java/com/helpmeCookies/user/dto/request/UserReq.java index ff9055b..e0284ea 100644 --- a/src/main/java/com/helpmeCookies/user/dto/request/UserReq.java +++ b/src/main/java/com/helpmeCookies/user/dto/request/UserReq.java @@ -3,6 +3,7 @@ import java.util.List; import com.helpmeCookies.product.entity.HashTag; +import com.helpmeCookies.user.dto.UserCommonInfoDto; import com.helpmeCookies.user.dto.UserDto; import com.helpmeCookies.user.dto.UserInfoDto; @@ -16,5 +17,21 @@ public record UserReq( String userImageUrl, String nickname ) { + public UserInfoDto toUserInfoDto() { + return new UserInfoDto( + name(), + email(), + birthdate(), + phone(), + address(), + hashTags() + ); + } + public UserCommonInfoDto toUserCommonInfoDto() { + return new UserCommonInfoDto( + nickname(), + userImageUrl() + ); + } } \ No newline at end of file diff --git a/src/main/java/com/helpmeCookies/user/dto/response/ArtistDetailsRes.java b/src/main/java/com/helpmeCookies/user/dto/response/ArtistDetailsRes.java index ead04ea..71dbaa5 100644 --- a/src/main/java/com/helpmeCookies/user/dto/response/ArtistDetailsRes.java +++ b/src/main/java/com/helpmeCookies/user/dto/response/ArtistDetailsRes.java @@ -9,8 +9,8 @@ public record ArtistDetailsRes( String description, Long totalFollowers, Long totalLikes, - String about - + String about, + String ImageUrl ) { public static ArtistDetailsRes from(ArtistInfoDto artistInfoDto, BusinessArtistDto businessArtistDto) { return new ArtistDetailsRes( @@ -18,7 +18,8 @@ public static ArtistDetailsRes from(ArtistInfoDto artistInfoDto, BusinessArtistD businessArtistDto.headName(), artistInfoDto.totalFollowers(), artistInfoDto.totalLikes(), - artistInfoDto.about() + artistInfoDto.about(), + artistInfoDto.artistImageUrl() ); } @@ -28,7 +29,8 @@ public static ArtistDetailsRes from(ArtistInfoDto artistInfoDto, StudentArtistDt studentArtistDto.schoolName(), artistInfoDto.totalFollowers(), artistInfoDto.totalLikes(), - artistInfoDto.about() + artistInfoDto.about(), + artistInfoDto.artistImageUrl() ); } } diff --git a/src/main/java/com/helpmeCookies/user/dto/response/UserImageResponse.java b/src/main/java/com/helpmeCookies/user/dto/response/UserImageResponse.java new file mode 100644 index 0000000..b58fb47 --- /dev/null +++ b/src/main/java/com/helpmeCookies/user/dto/response/UserImageResponse.java @@ -0,0 +1,8 @@ +package com.helpmeCookies.user.dto.response; + +import java.util.List; + +public record UserImageResponse( + List userImageUrl +) { +} diff --git a/src/main/java/com/helpmeCookies/user/entity/User.java b/src/main/java/com/helpmeCookies/user/entity/User.java index 2ca3903..2252d44 100644 --- a/src/main/java/com/helpmeCookies/user/entity/User.java +++ b/src/main/java/com/helpmeCookies/user/entity/User.java @@ -7,6 +7,7 @@ import org.springframework.data.jpa.domain.support.AuditingEntityListener; import org.springframework.format.annotation.DateTimeFormat; +import com.helpmeCookies.global.entity.BaseTimeEntity; import com.helpmeCookies.product.entity.HashTag; import jakarta.persistence.CollectionTable; @@ -35,7 +36,7 @@ @AllArgsConstructor @Builder @EntityListeners(AuditingEntityListener.class) -public class User { +public class User extends BaseTimeEntity { @Id @GeneratedValue(strategy = GenerationType.IDENTITY) @Column(nullable = false) @@ -48,11 +49,6 @@ public class User { @Embedded private UserInfo userInfo; - @DateTimeFormat(iso = DateTimeFormat.ISO.DATE_TIME) - @CreatedDate - @Column(nullable = false, updatable = false) - protected LocalDateTime createdAt; - public void updateUserCommonInfo(String nickname, String userImageUrl) { this.nickname = nickname; this.userImageUrl = userImageUrl; @@ -61,9 +57,4 @@ public void updateUserCommonInfo(String nickname, String userImageUrl) { public void updateUserInfo(UserInfo userInfo) { this.userInfo = userInfo; } - - private User setUserInfo(UserInfo userInfo) { - this.userInfo = userInfo; - return this; - } } \ No newline at end of file diff --git a/src/main/java/com/helpmeCookies/user/repository/UserRepository.java b/src/main/java/com/helpmeCookies/user/repository/UserRepository.java index b6ce04c..8e01f68 100644 --- a/src/main/java/com/helpmeCookies/user/repository/UserRepository.java +++ b/src/main/java/com/helpmeCookies/user/repository/UserRepository.java @@ -12,4 +12,5 @@ public interface UserRepository extends JpaRepository, UserCustomRepository { Optional findById(Long id); Optional findByUserInfoEmail(String email); + boolean existsByNicknameAndIdNot(String nickname, Long userId); } diff --git a/src/main/java/com/helpmeCookies/user/service/UserService.java b/src/main/java/com/helpmeCookies/user/service/UserService.java index 39abc2a..1c0bc12 100644 --- a/src/main/java/com/helpmeCookies/user/service/UserService.java +++ b/src/main/java/com/helpmeCookies/user/service/UserService.java @@ -1,11 +1,17 @@ package com.helpmeCookies.user.service; +import java.io.IOException; +import java.util.List; + import org.springframework.data.domain.Page; import org.springframework.data.domain.Pageable; import org.springframework.stereotype.Service; import org.springframework.transaction.annotation.Transactional; +import org.springframework.web.multipart.MultipartFile; import com.helpmeCookies.global.exception.user.ResourceNotFoundException; +import com.helpmeCookies.global.utils.AwsS3FileUtils; +import com.helpmeCookies.user.dto.UserCommonInfoDto; import com.helpmeCookies.user.dto.UserDto; import com.helpmeCookies.user.dto.UserInfoDto; import com.helpmeCookies.user.dto.UserTypeDto; @@ -28,6 +34,7 @@ public class UserService { private final UserRepository userRepository; private final ArtistInfoRepository artistInfoRepository; private final SocialRepository socialRepository; + private final AwsS3FileUtils awsS3FileUtils; @Transactional @@ -39,25 +46,24 @@ public UserDto getUserInfo(Long userId) { } @Transactional - public UserDto updateUser(UserReq userReq, Long userId) { + public UserDto updateUser(UserCommonInfoDto userCommonInfoDto, UserInfoDto userInfoDto, Long userId) { User existingUser = userRepository.findById(userId) .orElseThrow(() -> new ResourceNotFoundException("존재하지 않는 유저입니다.")); - existingUser.updateUserCommonInfo(userReq.nickname(), userReq.userImageUrl()); - UserInfo userInfo = UserInfo.builder().name(userReq.name()) - .email(userReq.email()) - .birthdate(userReq.birthdate()) - .phone(userReq.phone()) - .address(userReq.address()) - .hashTags(userReq.hashTags()) - .build(); + if (userRepository.existsByNicknameAndIdNot(userCommonInfoDto.nickname(), existingUser.getId())) { + throw new DuplicateRequestException("이미 존재하는 닉네임입니다."); + } + existingUser.updateUserCommonInfo(userCommonInfoDto.nickname(), userCommonInfoDto.ImageUrl()); + + UserInfo userInfo = userInfoDto.toEntity(); existingUser.updateUserInfo(userInfo); return UserDto.fromEntity(userRepository.save(existingUser)); } + @Transactional public UserTypeDto getUserType(Long userId) { String usertype = artistInfoRepository.findByUserId(userId) diff --git a/src/main/resources/data.sql b/src/main/resources/data.sql index f765a99..3e8c706 100644 --- a/src/main/resources/data.sql +++ b/src/main/resources/data.sql @@ -1,81 +1,102 @@ -INSERT INTO users (nickname, email, birthdate, phone, address, created_at) +-- users 테이블 초기 데이터 +INSERT INTO users (nickname, user_image_url, name, email, birthdate, phone, address, created_date, modified_date) VALUES - ('JohnDoe', 'johndoe@example.com', '1990-01-15', '010-1234-5678', 'Seoul, South Korea', '2024-09-23T12:00:00'), - ('JaneSmith', 'janesmith@example.com', '1985-05-23', '010-9876-5432', 'Busan, South Korea', '2024-09-23T12:00:00'), - ('MikeJohnson', 'mikejohnson@example.com', '1992-03-10', '010-5678-1234', 'Incheon, South Korea', '2024-09-23T12:00:00'), - ('EmilyDavis', 'emilydavis@example.com', '1988-08-17', '010-8765-4321', 'Daegu, South Korea', '2024-09-23T12:00:00'), - ('DavidWilson', 'davidwilson@example.com', '1995-07-07', '010-1111-2222', 'Daejeon, South Korea', '2024-09-23T12:00:00'), - ('SophiaMiller', 'sophiamiller@example.com', '1989-02-25', '010-3333-4444', 'Gwangju, South Korea', '2024-09-23T12:00:00'), - ('JamesBrown', 'jamesbrown@example.com', '1993-11-30', '010-5555-6666', 'Ulsan, South Korea', '2024-09-23T12:00:00'), - ('OliviaTaylor', 'oliviataylor@example.com', '1996-05-05', '010-7777-8888', 'Jeonju, South Korea', '2024-09-23T12:00:00'), - ('BenjaminLee', 'benjaminlee@example.com', '1987-09-15', '010-9999-0000', 'Cheongju, South Korea', '2024-09-23T12:00:00'), - ('IsabellaClark', 'isabellaclark@example.com', '1991-12-12', '010-1122-3344', 'Suwon, South Korea', '2024-09-23T12:00:00'), - ('HenryWhite', 'henrywhite@example.com', '1986-04-18', '010-2233-4455', 'Seongnam, South Korea', '2024-09-23T12:00:00'), - ('MiaHarris', 'miaharris@example.com', '1994-10-10', '010-3344-5566', 'Pohang, South Korea', '2024-09-23T12:00:00'), - ('LucasMartin', 'lucasmartin@example.com', '1997-06-06', '010-4455-6677', 'Changwon, South Korea', '2024-09-23T12:00:00'), - ('EllaYoung', 'ellayoung@example.com', '1998-03-03', '010-5566-7788', 'Yeosu, South Korea', '2024-09-23T12:00:00'), - ('WilliamKing', 'williamking@example.com', '1983-08-08', '010-6677-8899', 'Jeju, South Korea', '2024-09-23T12:00:00'), - ('AmeliaScott', 'ameliascott@example.com', '1990-07-17', '010-7788-9900', 'Gimhae, South Korea', '2024-09-23T12:00:00'), - ('JackMoore', 'jackmoore@example.com', '1984-02-02', '010-8899-0011', 'Ansan, South Korea', '2024-09-23T12:00:00'), - ('AvaWalker', 'avawalker@example.com', '1999-11-11', '010-9900-1122', 'Guri, South Korea', '2024-09-23T12:00:00'), - ('DanielPerez', 'danielperez@example.com', '1992-05-21', '010-0011-2233', 'Yangsan, South Korea', '2024-09-23T12:00:00'), - ('LilyHall', 'lilyhall@example.com', '1991-01-01', '010-1122-3344', 'Iksan, South Korea', '2024-09-23T12:00:00'); --- User 1 (JohnDoe) -INSERT INTO user_hashtags (user_id, hash_tags) VALUES (1, 'DREAMLIKE'); - --- User 2 (JaneSmith) -INSERT INTO user_hashtags (user_id, hash_tags) VALUES (2, 'DREAMLIKE'); - --- User 3 (MikeJohnson) -INSERT INTO user_hashtags (user_id, hash_tags) VALUES (3, 'DREAMLIKE'); - --- User 4 (EmilyDavis) -INSERT INTO user_hashtags (user_id, hash_tags) VALUES (4, 'DREAMLIKE'); - --- User 5 (DavidWilson) -INSERT INTO user_hashtags (user_id, hash_tags) VALUES (5, 'DREAMLIKE'); - --- User 6 (SophiaMiller) -INSERT INTO user_hashtags (user_id, hash_tags) VALUES (6, 'DREAMLIKE'); - --- User 7 (JamesBrown) -INSERT INTO user_hashtags (user_id, hash_tags) VALUES (7, 'DREAMLIKE'); - --- User 8 (OliviaTaylor) -INSERT INTO user_hashtags (user_id, hash_tags) VALUES (8, 'DREAMLIKE'); - --- User 9 (BenjaminLee) -INSERT INTO user_hashtags (user_id, hash_tags) VALUES (9, 'DREAMLIKE'); - --- User 10 (IsabellaClark) -INSERT INTO user_hashtags (user_id, hash_tags) VALUES (10, 'DREAMLIKE'); - --- User 11 (HenryWhite) -INSERT INTO user_hashtags (user_id, hash_tags) VALUES (11, 'DREAMLIKE'); - --- User 12 (MiaHarris) -INSERT INTO user_hashtags (user_id, hash_tags) VALUES (12, 'DREAMLIKE'); - --- User 13 (LucasMartin) -INSERT INTO user_hashtags (user_id, hash_tags) VALUES (13, 'DREAMLIKE'); - --- User 14 (EllaYoung) -INSERT INTO user_hashtags (user_id, hash_tags) VALUES (14, 'DREAMLIKE'); + ('johndoe1', 'https://example.com/johndoe1.jpg', 'John Doe 1', 'john.doe1@example.com', '1990-01-01', '123-456-7890', '123 Main St, City, Country', NOW(), NOW()), + ('johndoe2', 'https://example.com/johndoe2.jpg', 'John Doe 2', 'john.doe2@example.com', '1991-01-01', '123-456-7891', '124 Main St, City, Country', NOW(), NOW()), + ('johndoe3', 'https://example.com/johndoe3.jpg', 'John Doe 3', 'john.doe3@example.com', '1992-01-01', '123-456-7892', '125 Main St, City, Country', NOW(), NOW()), + ('johndoe4', 'https://example.com/johndoe4.jpg', 'John Doe 4', 'john.doe4@example.com', '1993-01-01', '123-456-7893', '126 Main St, City, Country', NOW(), NOW()), + ('johndoe5', 'https://example.com/johndoe5.jpg', 'John Doe 5', 'john.doe5@example.com', '1994-01-01', '123-456-7894', '127 Main St, City, Country', NOW(), NOW()), + ('janedoe1', 'https://example.com/janedoe1.jpg', 'Jane Doe 1', 'jane.doe1@example.com', '1990-02-01', '987-654-3210', '223 Main St, City, Country', NOW(), NOW()), + ('janedoe2', 'https://example.com/janedoe2.jpg', 'Jane Doe 2', 'jane.doe2@example.com', '1991-02-01', '987-654-3211', '224 Main St, City, Country', NOW(), NOW()), + ('janedoe3', 'https://example.com/janedoe3.jpg', 'Jane Doe 3', 'jane.doe3@example.com', '1992-02-01', '987-654-3212', '225 Main St, City, Country', NOW(), NOW()), + ('janedoe4', 'https://example.com/janedoe4.jpg', 'Jane Doe 4', 'jane.doe4@example.com', '1993-02-01', '987-654-3213', '226 Main St, City, Country', NOW(), NOW()), + ('janedoe5', 'https://example.com/janedoe5.jpg', 'Jane Doe 5', 'jane.doe5@example.com', '1994-02-01', '987-654-3214', '227 Main St, City, Country', NOW(), NOW()); + +-- user_hashtags 테이블 초기 데이터 +INSERT INTO user_hashtags (user_id, hash_tags) +VALUES + (1, 'SERENITY'), + (1, 'JOYFUL'), + (2, 'MELANCHOLY'), + (2, 'NOSTALGIA'), + (3, 'VIBRANCE'), + (3, 'WONDER'), + (4, 'DREAMLIKE'), + (5, 'CONTEMPLATION'), + (6, 'JOYFUL'), + (7, 'LONELINESS'), + (8, 'MYSTERY'), + (9, 'SERENITY'), + (10, 'NOSTALGIA'); + +-- artist_info 테이블 초기 데이터 +INSERT INTO artist_info (user_id, nickname, artist_image_url, artist_type, total_followers, total_likes, about) +VALUES + (1, 'ArtistJohn1', 'https://example.com/artistjohn1.jpg', 'BUSINESS', 100, 200, 'About Artist John 1'), + (2, 'ArtistJohn2', 'https://example.com/artistjohn2.jpg', 'STUDENT', 150, 300, 'About Artist John 2'), + (3, 'ArtistJane1', 'https://example.com/artistjane1.jpg', 'BUSINESS', 120, 220, 'About Artist Jane 1'), + (4, 'ArtistJane2', 'https://example.com/artistjane2.jpg', 'STUDENT', 130, 250, 'About Artist Jane 2'); --- User 15 (WilliamKing) -INSERT INTO user_hashtags (user_id, hash_tags) VALUES (15, 'DREAMLIKE'); +-- business_artist 테이블 초기 데이터 +INSERT INTO business_artist (artist_info_id, business_number, open_date, head_name) +VALUES + (1, 'B123456789', '2000-01-01', 'John Head 1'), + (3, 'B987654321', '2005-02-01', 'Jane Head 1'); --- User 16 (AmeliaScott) -INSERT INTO user_hashtags (user_id, hash_tags) VALUES (16, 'DREAMLIKE'); +-- student_artist 테이블 초기 데이터 +INSERT INTO student_artist (artist_info_id, school_email, school_name, major) +VALUES + (2, 'john2@university.com', 'University A', 'Fine Arts'), + (4, 'jane2@university.com', 'University B', 'Visual Arts'); --- User 17 (JackMoore) -INSERT INTO user_hashtags (user_id, hash_tags) VALUES (17, 'DREAMLIKE'); +-- social 테이블 초기 데이터 +INSERT INTO social (follower_id, following_id) +VALUES + (1, 2), + (1, 3), + (2, 4), + (3, 1), + (4, 2); + +-- product 테이블 초기 데이터 삽입 +INSERT INTO product (name, category, size, price, description, preferred_location, thumbnail_url, artist_info_id, created_date, modified_date) +VALUES + ('Mountain Landscape', 'PICTURE', '100x150', 1500000, 'Beautiful mountain landscape painting.', 'Seoul, South Korea', 'https://example.com/thumbnail1.jpg', 1, NOW(), NOW()), + ('Modern Sculpture', 'PIECE', '50x80', 2500000, 'Modern art sculpture made of steel.', 'New York, USA', 'https://example.com/thumbnail2.jpg', 3, NOW(), NOW()), + ('Oriental Artwork', 'ORIENTAL', '120x180', 2000000, 'Traditional oriental painting.', 'Beijing, China', 'https://example.com/thumbnail3.jpg', 2, NOW(), NOW()); --- User 18 (AvaWalker) -INSERT INTO user_hashtags (user_id, hash_tags) VALUES (18, 'DREAMLIKE'); +-- product_hashtags 테이블 초기 데이터 삽입 +INSERT INTO product_hashtags (product_id, hash_tags) +VALUES + (1, 'SERENITY'), + (1, 'VIBRANCE'), + (2, 'CONTEMPLATION'), + (3, 'MYSTERY'), + (3, 'DREAMLIKE'); + +-- product_image 테이블 초기 데이터 삽입 +INSERT INTO product_image (photo_url, product_id, uuid) +VALUES + ('https://example.com/product1_image1.jpg', 1, 'uuid-1234'), + ('https://example.com/product1_image2.jpg', 1, 'uuid-5678'), + ('https://example.com/product2_image1.jpg', 2, 'uuid-91011'), + ('https://example.com/product3_image1.jpg', 3, 'uuid-121314'); --- User 19 (DanielPerez) -INSERT INTO user_hashtags (user_id, hash_tags) VALUES (19, 'DREAMLIKE'); +-- likes 테이블 초기 데이터 삽입 +INSERT INTO likes (user_id, product_id) +VALUES + (1, 1), + (2, 1), + (3, 2), + (4, 3), + (5, 3); + +-- orders 테이블 초기 데이터 삽입 +INSERT INTO orders (user_id, product_id, status) +VALUES + (1, 1, 'ORDER'), + (2, 2, 'ORDER'), + (3, 3, 'CANCEL'), + (4, 1, 'ORDER'), + (5, 2, 'CANCEL'); --- User 20 (LilyHall) -INSERT INTO user_hashtags (user_id, hash_tags) VALUES (20, 'DREAMLIKE');