업데이트 중 내가 맡은 역할 - 관리자 페이지 만들기
만들어 줄 기능
✔️ 관리자 회원 전체 조회
HTTPMETHOD GET
http://{{host}}/admin/members/info?page=1&size=10
HTTPREQUEST 200 OK
HTTPREQUEST 401 Unauthorized / message : 401 - Unauthorized
✔️ 회원 전체 조회 페이지에서 Delete 메서드로 회원 삭제
HTTPMETHOD DELETE
http://{{host}}/admin/members/{member-id}
HTTPREQUEST 204 No Content
HTTPREQUEST 401 Unauthorized / message : 401 - Unauthorized
✔️ 관리자 회원 개별 조회 페이지
http://{{host}}/admin/members/{member-id}/manage
HTTPREQUEST 200 OK
HTTPREQUEST 400 Bad Request / message : 400 - not found
HTTPREQUEST 401 Unauthorized / message : 401 - Unauthorized
✔️ 관리자 회원 개별 조회 페이지에서 게시글 삭제, 댓글 삭제, 대댓글 삭제 (각 Delete요청 보내기)
http://{{host}}/admin/members/{member-id}/boards/{board-id}
http://{{host}}/admin/members/{member-id}/answers/{answer-id}
http://{{host}}/admin/members/{member-id}/comment/{comment-id}
HTTPREQUEST 204 No Content
HTTPREQUEST 400 Bad Request / message : 400 - not found
HTTPREQUEST401 Unauthorized / message : 401 - Unauthorized
SecurityConfiguration
기존 SecurityConfiguration 추가
기존 내용에서 접근 권한을 추가하여 ADMIN 권한을 가진 사용자만 ("/admin/members/**") URI 에 접근할 수 있도록 했다.
기존 MemberAccessDeniedHandler에서 수정
+) 만약 관리자 페이지로 ADMIN 권한이 없는 사람이 접근했을 때 메인 화면으로 리다이렉트하는 메서드도 추가했다.
// 만약에 접근 권한 없는 사용자가 들어왔을 때는 메인 페이지로 리다이렉트
if(request.getRequestURI().startsWith("/admin/members")){
response.sendRedirect("/");
}
AdminController
관리자 회원 전체 조회하는 getMembers 메서드
🔻 AdminController.getMembers 메서드
회원들이 볼 수 있는 회원 조회 페이지와 관리자가 보는 회원 조회 페이지의 나타나는 필드들이 달라야 하기 때문에 DTO를 만들어 주었다.
🔻 MemberAdminListResponseDto
package com.codestates.server.domain.member.dto;
import lombok.Getter;
import lombok.Setter;
// 관리자 페이지에서 리스트형태로 회원 정보 보일 것들
@Getter
@Setter
public class MemberAdminListResponseDto {
private String memberId;
private String email;
private String name;
private String profileImage;
private Long point;
}
관리자 회원 전체 조회 페이지에서 회원삭제할 수 있는 deleteMethod 추가
🔻 AdminController.deleteMember 메서드
🚨 문제 발생
데이터 무결성 제약 조건 위반으로 에러 발생
나는 POINT_HISTORY라는 테이블을 만든 적이 없는데 갑자기 POINT_HISTORY라는 테이블에서 MEMBER를 참조하고 있기 때문에 데이터 무결성 제약 조건이 위반된다는 것이다... 띠용~~
나는 분명 MEMBER에서 cascade= CASCADE.ALL 해서 회원을 삭제 하면 모두 삭제 되게 영속성 전이를 시켜놨는데 이 무슨 황당한 소리인가 싶었다.
import com.codestates.server.domain.answer.entity.Answer;
import com.codestates.server.domain.board.entity.Board;
import com.codestates.server.domain.bookmark.entity.Bookmark;
import com.codestates.server.domain.comment.entity.Comment;
import com.fasterxml.jackson.annotation.JsonIgnore;
import lombok.*;
import javax.persistence.*;
import java.util.ArrayList;
import java.util.List;
@Getter
@Setter
@RequiredArgsConstructor
@Entity
public class Member {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long memberId;
private String email;
private String name; // 닉네임
private String phone;
private String password;
private String profileImage;
private Long point; //계산된 포인트값
// 멤버 당 하나의 권한을 가지기 때문에 즉시 로딩 괜찮음 (즉시로딩 N : 1은 괜찮으나 1:N은 안됨)
// 사용자 등록 시 사용자의 권한 등록을 위해 권한 테이블 생성
@ElementCollection(fetch = FetchType.EAGER)
private List<String> roles = new ArrayList<>();
@JsonIgnore
@OneToMany(mappedBy = "member", cascade = CascadeType.ALL)
private List<Board> boards;
@JsonIgnore
@OneToMany(mappedBy = "member", cascade = CascadeType.ALL)
private List<Answer> answers;
@JsonIgnore
@OneToMany(mappedBy = "member", cascade = CascadeType.ALL)
private List<Comment> comments;
@JsonIgnore
@OneToMany(mappedBy = "member", cascade = CascadeType.ALL)
private List<Bookmark> Bookmarks;
}
그래서 뭐지 뭐지 뭐지 하다가 살펴 보았더니 업그레이드를 하며 팀원 중 한 분이 만들어 놓은 테이블이었다. 왜 PR된 것도 머지 된 것도 몰랐을까..? ^_- 소통의 중요성을 다시 한 번 깨닫는 순간이었다.
그래서 PointHistory라는 곳에 가서 살펴보았다.
import com.codestates.server.domain.member.entity.Member;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import lombok.RequiredArgsConstructor;
import javax.persistence.*;
import java.time.LocalDateTime;
@Entity
@NoArgsConstructor
public class PointHistory {
public PointHistory(Long point, Member member, PointHistoryType pointHistoryType) {
this.point = point;
this.member = member;
this.pointHistoryType = pointHistoryType;
}
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
@Column
private Long point;
@ManyToOne
private Member member;
@Column
private PointHistoryType pointHistoryType;
@Column(nullable = false)
private LocalDateTime createdAt = LocalDateTime.now();
}
여기서 Member를 외래키로 참조하고 있으면서 Member가 변경이 있을 때 함께 변경을 해주는 옵션 사항이 붙어있지 않아 문제가 발생했던 것이다.
해결할 수 있는 방법은 여러 개가 있었지만 어차피 Member 페이지에서 포인트 내역을 보여줘야 하기도 하고 같이 삭제를 해줘야 하기 때문에 Member 엔티티에 List<PointHistory>를 추가해주었다.
문제는 해결완료! +_+✨
그리고 관리자 페이지에서 삭제가 잘 되는 것을 확인! 했다.
소통을 잘 하고 공유를 잘 하자...!!!! 다시 깨달았다
회원 개별 정보 조회 페이지 만들기
- 회원이 보는 본인의 마이페이지와는 또 다른 response값
- board, answer, comment 추가 및 password 없는 DTO 생성
🔻 AdminController.getMember 메서드
회원 있는지 찾고 있으면 회원 정보 response
🔻 MemberAdminResponseDto 추가
import com.codestates.server.domain.answer.entity.Answer;
import com.codestates.server.domain.board.entity.Board;
import com.codestates.server.domain.comment.entity.Comment;
import com.codestates.server.domain.pointhistory.entity.PointHistory;
import lombok.AllArgsConstructor;
import lombok.Getter;
import lombok.Setter;
import java.util.List;
@Getter
@Setter
@AllArgsConstructor
public class MemberAdminResponseDto {
private String memberId;
private String email;
private String name;
private String phone;
private String profileImage;
private Long point;
private List<PointHistory> pointHistories;
private List<Board> boards;
private List<Answer> answers;
private List<Comment> comments;
}
회원이 작성한 board 삭제하는 deleteBoard 메서드 작성하기
🔻 AdminContorller.deleteBoard 메서드
🔻 AnswerService.deleteAdminBoard 메서드
회원이 작성한 Board 삭제하는 메서드인 deleteAdminBoard 메서드 추가
* 이전에 작성해둔 deleteBoard 메서드는 본인인지 token을 확인하는 작업이 들어가기 때문에 Admin이 삭제할 수 있는 메서드를 따로 추가해주었다.
🔻 AdminContorller.deleteAnswer 메서드
🔻 AnswerService.deleteAdminAnswer 메서드
회원이 작성한 Answer 삭제하는 메서드 deleteAdminAnswer 메서드 추가
* 이전에 작성해둔 deleteAnswer 메서드는 본인인지 token을 확인하는 작업이 들어가기 때문에 Admin이 삭제할 수 있는 메서드를 따로 추가해주었다. (Board와 동일)
Comment 도 동일하게 작성해주었다.
🔻 AdminContorller.deleteComment 메서드
🔻 DeleteService.deleteComment 메서드
postman으로 테스트해보기
1. 관리자 토큰 없이 접근 불가
2. 관리자 회원 전체 조회
- `memberId, email, name, profileImage, point` 만 리스트로 출력
- pagination 적용하기
3. 관리자 회원 관리 - 회원 삭제
4. 관리자 회원 관리 - 회원 개별 페이지 조회
`memberId, email, name, phone, profileImage, point, pointHistories, boards, answers, comments` 출력
5. 관리자 회원 관리 - 게시글 삭제
6. 관리자 회원 관리 - 댓글 삭제
7. 관리자 회원 관리 - 대댓글 삭제
💬 느낀 점
기존에 있던 메서드들로 대부분 사용해서 크게 어려움 없이 작성할 수 있었던 Admin 페이지 만들기!
Security에 대한 기본적인 흐름이나 이해가 있어야 작성이 가능할 것 같다는 생각이 들었다.
Spring Security와 관련한 정리도 빠른 시일 내에 하도록 해야겠다 : )
이번에 겹치는 부분들이 많아서 conflict가 많이 나지 않을까 많이 걱정이 되기도 하는데 😶 그만큼 소통이 더욱 더 중요하지 않을까 생각이 든다!!
남은 기능들도 얼른 끝내고 정리해야징~~! 홧티이이이이오이잉잉
"이 포스팅은 쿠팡 파트너스 활동의 일환으로, 이에 따른 일정액의 수수료를 제공받습니다."
'FRAMEWORK > SPRING' 카테고리의 다른 글
[Spring Boot] 스프링 부트 프로젝트 시작하기 / 프로젝트 생성하고 git 연동시키기 (1) | 2024.06.27 |
---|---|
[SPRING] spring boot 관리자 페이지 테스트 코드 작성하기 / 프로젝트 업그레이드 시키기 (2) | 2023.11.21 |
[SPRING] 작업 환경 분리하기 / 프로젝트 개발 환경, 배포 환경 profile 작업 (0) | 2023.11.15 |
[SPRING] 스프링 부트에서 의존성 못 찾을 때 `create class com.mysql.cj.jdbc.Driver` 에러 해결 방법 (0) | 2023.11.06 |
[SPRING] 스프링 의존성 주입(DI) 방법 / 생성자 주입, 필드 주입, setter 주입 (1) | 2023.10.17 |