[Spring Boot] 추천(좋아요) 구현하기

DANI·2023년 10월 16일
0
post-thumbnail

💻 게시판의 질문, 답변에 추천 기능을 추가해보자!

💾 Question과 Answer 엔티티에 voter 속성을 추가

@ManyToMany // 추천은 하나의 질문에 여러사람이, 한 사람이 여러개의 질문을 추천할 수 있다
private Set<SiteUser> voter; // 추천인에 해당되는 필드

추천인은 중복이 되면 안되기 때문에 Set을 사용했다.

💻 h2데이터베이스 콘솔에 접속해보자

voter 속성이 추가되었다. @ManyToMany 관계로 속성을 생성하면 새로운 테이블을 생성하여 데이터를 관리한다. 테이블에는 서로 연관된 엔티티의 고유번호(id) 2개가 프라이머리 키로 되어 있기 때문에 다대다(N:N) 관계가 성립하는 구조



📩 1. 질문 추천 하기

💾 추천 버튼 만들기(question_detail.html 템플릿 수정)

✅ 원하는 위치에 질문 추천버튼을 추가해보자!

<div class = "m-2">
<a href="javascript:void(0);" class="recommend badge rounded-pill bg-light text-dark" th:data-uri="@{|/question/vote/${question.id}|}"><img src="\recommend.png" alt="사진없음" width="20" height="20"><span class="badge rounded-pill bg-danger" th:text="${#lists.size(question.voter)}"></span></a>
</div>

삭제 구현시와 유사하다. 이제 자바스크립트를 이용하여 recommend event를 작성해보자!


💾 추천 이벤트 만들기(question_detail.html 템플릿 수정)

✅ 추천 버튼을 누르면 "정말로 추천하시겠습니까?"라는 확인창이 뜨는 자바스크립트 추가하기!

<!-- 삭제 -->
<script layout:fragment="script" type='text/javascript'>
const delete_elements = document.getElementsByClassName("delete");
Array.from(delete_elements).forEach(function(element) {
    element.addEventListener('click', function() {
        if(confirm("정말로 삭제하시겠습니까?")) {
            location.href = this.dataset.uri;
        };
    });
});
<!-- 추천 -->
const recommend_elements = document.getElementsByClassName("recommend");
Array.from(recommend_elements).forEach(function(element) {
    element.addEventListener('click', function() {
        if(confirm("정말로 추천하시겠습니까?")) {
            location.href = this.dataset.uri;
        };
    });
});
<!-- 가장 아래에 <script>엘리먼트를 삽입한다 -->
</html> 

삭제기능과 유사하다


💾 QuestionService에 vote 메소드 추가

✅ vote 메소드 추가

public void vote(Question question, SiteUser siteUser) {
        // 질문 엔티티에 사용자를 추천인으로 저장한다.
		question.getVoter().add(siteUser);
		this.questionRepository.save(question); // 현재 질문 저장
}

💾 QuestionController에 @{|/question/vote/${question.id}|} 매핑하기

✅ vote 메소드 추가

@PreAuthorize("isAuthenticated()")
@GetMapping("/vote/{id}")
public String questionVote(Principal principal, @PathVariable("id") Integer id) {
            // 파라미터로 받은 id를 조회하여 질문을 저장
	        Question question = this.questionService.getQuestion(id);
            // 현재 객체의 id를 조회하여 사용자를 저장
	        SiteUser siteUser = this.userService.getUser(principal.getName());
            // 서비스의 vote 메소드 사용
	        this.questionService.vote(question, siteUser);
            // id페이지로 리다이렉트
	        return String.format("redirect:/question/detail/%s", id);
	    }

💻 실행화면

추천 버튼이 생성되었다!


"정말로 추천하시겠습니까?" 팝업창이 생성된다! 확인을 눌러보자!


추천되었고, 추천수가 추가되었으며, 질문 상세페이지로 리다이렉트 된다!





📩 2. 답변 추천 하기

💾 추천 버튼 만들기(question_detail.html 템플릿 수정)

✅ 원하는 위치에 답변 추천버튼을 추가해보자!

<div class = "m-2">
<a href="javascript:void(0);" class="recommend badge rounded-pill bg-light text-dark" th:data-uri="@{|/answer/vote/${answer.id}|}"><img src="\recommend.png" alt="사진없음" width="20" height="20"><span class="badge rounded-pill bg-danger" th:text="${#lists.size(answer.voter)}"></span></a>
</div>

매핑 주소를 제외하고 질문 추천 버튼과 유사하다.


💾 AnswerService에 vote 메소드 추가

✅ vote 메소드 추가

public void vote(Answer answer, SiteUser siteUser) {
    	answer.getVoter().add(siteUser);
    	this.answerRepository.save(answer);
}

질문 vote메소드와 유사하다


💾 AnswerController에 @{|/answer/vote/${answer.id}|} 매핑하기

✅ vote 메소드 추가

@PreAuthorize("isAuthenticated()")
@GetMapping("/vote/{id}")
public String answerVote(Principal principal, @PathVariable("id") Integer id) {
        Answer answer = this.answerService.getAnswer(id);
        SiteUser siteUser = this.userService.getUser(principal.getName());
        
        this.answerService.vote(answer, siteUser);
        return String.format("redirect:/question/detail/%s", answer.getQuestion().getId());
    }

질문 vote메소드와 유사하다



💻 실행화면

추천 버튼이 생성되었다!

"정말로 추천하시겠습니까?" 팝업창이 생성된다! 확인을 눌러보자!


추천되었고, 추천수가 업데이트됐으며 질문상세페이지로 리다이렉트 된다 / 추천글자는 그림으로 대체하였다.






✨ 이번 챕터에서 배운 부분

✅ ManyToMany 관계로 생성하면 새로운 테이블을 생성하여 데이터를 관리한다.
✅ click event 자바 스크립트 / 추천 이벤트
✅ 추천메소드에 현재 유저를 추천인으로 저장한다.

📝 공부할 부분

✅ 자바 스크립트 click event 공부하기
✅ layout 상속 복습
✅ 다대다 관계 공부
✅ Bigint 자료형 공부

0개의 댓글