Skip to content

Commit

Permalink
add : user ADMIN api 추가
Browse files Browse the repository at this point in the history
  • Loading branch information
kimgunwooo committed Nov 13, 2024
1 parent 02a9de5 commit ed268d3
Show file tree
Hide file tree
Showing 5 changed files with 144 additions and 11 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
package com.example.demo.domain.user.controller;

import com.example.demo.domain.user.domain.dto.request.UpdateUserInfoRequest;
import com.example.demo.domain.user.domain.dto.response.UserInfo;
import com.example.demo.domain.user.service.UserAdminService;
import com.example.demo.global.base.dto.ResponseBody;
import com.example.demo.global.base.dto.page.GlobalPageResponse;
import jakarta.validation.Valid;
import lombok.RequiredArgsConstructor;
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.ResponseEntity;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.web.bind.annotation.*;

import static com.example.demo.global.base.dto.ResponseUtil.createSuccessResponse;

@RequiredArgsConstructor
@RestController
@RequestMapping("/api/v1/admin/users")
@PreAuthorize("isAuthenticated() and hasRole('ROLE_ADMIN')")
public class UserAdminController {

private final UserAdminService userAdminService;

@GetMapping
public ResponseEntity<ResponseBody<GlobalPageResponse<UserInfo>>> getAllUsers (
@PageableDefault(page=0, size=10,sort = "createdAt", direction = Sort.Direction.DESC) Pageable pageable
) {
return ResponseEntity.ok(createSuccessResponse(userAdminService.getAllUsers(pageable)));
}

@PatchMapping("/{userId}")
public ResponseEntity<ResponseBody<Void>> updateUserInfo (@PathVariable Long userId, @Valid @RequestBody UpdateUserInfoRequest request) {
userAdminService.updateUserInfo(userId, request);
return ResponseEntity.ok(createSuccessResponse());
}

@DeleteMapping("/{userId}")
public ResponseEntity<ResponseBody<Void>> deleteUser (@PathVariable Long userId) {
userAdminService.deleteUser(userId);
return ResponseEntity.ok(createSuccessResponse());
}
}
38 changes: 28 additions & 10 deletions src/main/java/com/example/demo/domain/user/domain/User.java
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
import com.example.demo.domain.board.domain.entity.Like;
import com.example.demo.domain.newsletter.domain.Newsletter;
import com.example.demo.domain.seminar_application.domain.SeminarApplication;
import com.example.demo.domain.user.domain.dto.request.UpdateUserInfoRequest;
import com.example.demo.domain.user.domain.vo.Role;
import com.example.demo.domain.user_addtional_info.domain.UserAdditionalInfo;
import com.example.demo.global.base.domain.BaseEntity;
Expand Down Expand Up @@ -53,9 +54,10 @@ public class User extends BaseEntity {
@JoinColumn(name = "user_additional_info_id")
private UserAdditionalInfo userAdditionalInfo;

@OneToOne(fetch = FetchType.LAZY, cascade = CascadeType.ALL, orphanRemoval = true)
@JoinColumn(name = "news_letter_id")
private Newsletter newsletter;
// TODO. 추후 user 와 newsletter 연동이 확정되면 추가
// @OneToOne(fetch = FetchType.LAZY, cascade = CascadeType.ALL, orphanRemoval = true)
// @JoinColumn(name = "news_letter_id")
// private Newsletter newsletter;

@OneToMany(mappedBy = "user")
private List<Board> boards = new ArrayList<>();
Expand All @@ -78,10 +80,7 @@ public User(OAuth2Provider provider, String providerId, String nickname, Role ro
}

public void setInitialInfo(String nickname, String name, String defaultImageUrl) {
this.nickname = nickname;
this.name = name;
this.profileImageUrl = defaultImageUrl;
this.role = Role.ROLE_USER;

}

public void updateNickname(String nickname) {
Expand All @@ -92,9 +91,9 @@ public void mapAdditionalInfo(UserAdditionalInfo userAdditionalInfo) {
this.userAdditionalInfo = userAdditionalInfo;
}

public void mapNewsletter(Newsletter newsletter) {
this.newsletter = newsletter;
}
// public void mapNewsletter(Newsletter newsletter) {
// this.newsletter = newsletter;
// }

public void addSeminarApplications(SeminarApplication seminarApplication) {
this.seminarApplications.add(seminarApplication);
Expand All @@ -111,4 +110,23 @@ public void updateUserRoleToSeminarWriter() {
public void changeProfileUrl(String profileImageUrl) {
this.profileImageUrl = profileImageUrl;
}

public Boolean isAdmin() {
return Role.ROLE_ADMIN.equals(this.role);
}

public void updateUserInfo(UpdateUserInfoRequest request) {
this.nickname = request.nickname();
this.name = request.name();
this.profileImageUrl = request.profileImageUrl();
this.role = request.role();
}

// public boolean hasNewsletter() {
// return this.newsletter != null;
// }

public void setDefaultProfileUrl(String defaultImageUrl) {
this.profileImageUrl = defaultImageUrl;
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
package com.example.demo.domain.user.domain.dto.request;

import com.example.demo.domain.user.domain.vo.Role;
import com.example.demo.global.aop.valid.ValidEnum;
import jakarta.validation.constraints.NotBlank;
import jakarta.validation.constraints.Pattern;

import static com.example.demo.global.regex.S3UrlRegex.S3_PROFILE_FILE_URL;
import static com.example.demo.global.regex.UserRegex.NICKNAME_REGEXP;

public record UpdateUserInfoRequest(
@Pattern(regexp = NICKNAME_REGEXP, message = "닉네임 정규식을 맞춰주세요.") String nickname,
@NotBlank(message = "이름은 빈값일 수 없습니다.") String name,
@Pattern(regexp = S3_PROFILE_FILE_URL) String profileImageUrl,
@ValidEnum(enumClass = Role.class) Role role
) {
}
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ public record UserInfo(
OAuth2Provider provider,
String nickname,
String name,
String profileImage,
String profileImageUrl,
Role role,
@JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "yyyy-MM-dd'T'HH:mm:ss")
LocalDateTime createdAt,
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
package com.example.demo.domain.user.service;

import com.example.demo.domain.user.domain.User;
import com.example.demo.domain.user.domain.dto.request.UpdateUserInfoRequest;
import com.example.demo.domain.user.domain.dto.response.UserInfo;
import com.example.demo.domain.user.repository.UserRepository;
import com.example.demo.global.base.dto.page.GlobalPageResponse;
import jakarta.validation.Valid;
import lombok.RequiredArgsConstructor;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.Pageable;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.Optional;

@Transactional(readOnly = true)
@RequiredArgsConstructor
@Service
public class UserAdminService {

private final UserRepository userRepository;
private final UserService userService;

public Boolean isAdmin(Long userId) {
Optional<User> userOptional = userRepository.findById(userId);

if (userOptional.isPresent()) {
User user = userOptional.get();
return user.isAdmin();
}

return false;
}

public GlobalPageResponse<UserInfo> getAllUsers(Pageable pageable) {
Page<UserInfo> userInfoPage = userRepository.findAll(pageable).map(UserInfo::from);
return GlobalPageResponse.create(userInfoPage);
}

@Transactional
public void updateUserInfo(Long userId, UpdateUserInfoRequest request) {
User user = userService.validateUser(userId);
userService.checkNicknameDuplicate(request.nickname());
user.updateUserInfo(request);
}

@Transactional
public void deleteUser(Long userId) {
userRepository.deleteById(userId);
}
}

0 comments on commit ed268d3

Please sign in to comment.