Skip to content

Commit

Permalink
따봉 기능 구현
Browse files Browse the repository at this point in the history
type: feat, change, test
body: 따봉 기능을 추가 하였습니다. 기존 릴리즈 노트 정보에 따봉 갯수가 추가됩니다.
  • Loading branch information
kjk7212 committed Aug 7, 2023
1 parent cda8b55 commit 73c0fa0
Show file tree
Hide file tree
Showing 15 changed files with 477 additions and 32 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
package com.swave.urnr.releasenote.controller;

import com.swave.urnr.releasenote.responsedto.LikedCountResponseDTO;
import com.swave.urnr.releasenote.service.LikedService;
import com.swave.urnr.util.http.HttpResponse;
import io.swagger.annotations.Api;
import io.swagger.v3.oas.annotations.Operation;
import lombok.RequiredArgsConstructor;
import org.springframework.web.bind.annotation.*;

import javax.servlet.http.HttpServletRequest;

@Api(tags = "LikedController")
@RestController
@RequiredArgsConstructor
@CrossOrigin(origins = "http://localhost:3000", allowedHeaders = "*", allowCredentials = "true")
public class LikedController {

private final LikedService likedService;

@Operation(summary = "내 이름 좋아요 하나 생성", description = "releaseNoteId의 릴리즈 노트에 내 이름으로 좋아요를 하나 생성합니다. 중복은 불가능 합니다. 유저 정보는 JWT로부터 가져옵니다.")
@PostMapping("/api/project/release-note/{releaseNoteId}/Liked")
public HttpResponse createLiked(HttpServletRequest request,@PathVariable Long releaseNoteId){
return likedService.createLiked(request, releaseNoteId);
}

@Operation(summary = "내 이름 좋아요 하나 취소", description = "releaseNoteId의 릴리즈 노트에 내 이름으로된 좋아요를 하나 취소합니다. 유저 정보는 JWT로부터 가져옵니다.")
@PutMapping("/api/project/release-note/{releaseNoteId}/Liked")
public HttpResponse cancelLiked(HttpServletRequest request,@PathVariable Long releaseNoteId){
return likedService.cancelLiked(request, releaseNoteId);
}

@Operation(summary = "좋아요 갯수 세기", description = "releaseNoteId의 릴리즈 노트에 달린 좋아요의 갯수를 반환합니다.")
@GetMapping("/api/project/release-note/{releaseNoteId}/Liked")
public LikedCountResponseDTO countLiked(@PathVariable Long releaseNoteId){
return likedService.countLiked(releaseNoteId);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -116,7 +116,6 @@ public ReleaseNoteContentResponseDTO makeReleaseNoteContentDTO(){
}

releaseNoteContentResponseDTO.setComment(commentContentList);
//releaseNoteContentDTO.setLiked(this);

return releaseNoteContentResponseDTO;
}
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
package com.swave.urnr.releasenote.repository;

public interface LikedCustomRepository {
long countByLiked(Long userInProjectId);
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
package com.swave.urnr.releasenote.repository;

import com.querydsl.jpa.impl.JPAQueryFactory;

import static com.swave.urnr.releasenote.domain.QLiked.liked;
import static com.swave.urnr.releasenote.domain.QReleaseNote.releaseNote;
import static com.swave.urnr.releasenote.domain.QSeenCheck.seenCheck;

public class LikedCustomRepositoryImpl implements LikedCustomRepository {
private final JPAQueryFactory jpaQueryFactory;

public LikedCustomRepositoryImpl(JPAQueryFactory jpaQueryFactory) {
this.jpaQueryFactory = jpaQueryFactory;
}

@Override
public long countByLiked(Long releaseNoteId){
return jpaQueryFactory
.select(liked.count())
.from(releaseNote)
.join(seenCheck).on(seenCheck.releaseNote.id.eq(releaseNote.id))
.join(liked).on(liked.seenCheck.id.eq(seenCheck.id))
.where(seenCheck.isDeleted.eq(false), releaseNote.isDeleted.eq(false), releaseNote.id.eq(releaseNoteId), liked.isLiked.eq(true))
.fetchFirst();
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
package com.swave.urnr.releasenote.repository;

import com.swave.urnr.releasenote.domain.Liked;
import org.springframework.data.jpa.repository.JpaRepository;

public interface LikedRepository extends JpaRepository<Liked, Long>, LikedCustomRepository {
Liked findBySeenCheck_Id(Long Id);
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
package com.swave.urnr.releasenote.responsedto;

import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import lombok.NoArgsConstructor;

@Data
@ApiModel(value = "좋아요 개수 카운트 DTO")
@NoArgsConstructor
public class LikedCountResponseDTO {
@ApiModelProperty(value="좋아요 개수", example = "2", required = true)
private Long likedCount;
}
Original file line number Diff line number Diff line change
Expand Up @@ -14,26 +14,26 @@
@NoArgsConstructor
public class ReleaseNoteContentResponseDTO {

@ApiModelProperty(value="글쓴이", example = "전강훈", required = true)
@ApiModelProperty(value = "글쓴이", example = "전강훈", required = true)
private String creator;
@ApiModelProperty(value="릴리즈 노트 버전", example = "1.0.0", required = true)
@ApiModelProperty(value = "릴리즈 노트 버전", example = "1.0.0", required = true)
private String version;
@JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "Asia/Seoul")
@ApiModelProperty(value="최종 수정 시각", example = "2023-07-09", required = true)
@ApiModelProperty(value = "최종 수정 시각", example = "2023-07-09", required = true)
private Date lastModified;
@JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "Asia/Seoul")
@ApiModelProperty(value="릴리즈 날짜", example = "2023-07-08", required = true)
@ApiModelProperty(value = "릴리즈 날짜", example = "2023-07-08", required = true)
private Date releaseDate;
@ApiModelProperty(value="세 줄 요약", example = "DELL의 성능을 조정했습니다.", required = true)
@ApiModelProperty(value = "세 줄 요약", example = "DELL의 성능을 조정했습니다.", required = true)
private String summary;
@ApiModelProperty(value="노트 블럭 리스트", required = true)
@ApiModelProperty(value = "노트 블럭 리스트", required = true)
private List<NoteBlockContentResponseDTO> blocks;
@ApiModelProperty(value="댓글 리스트", required = true)
@ApiModelProperty(value = "댓글 리스트", required = true)
private List<CommentContentResponseDTO> comment;
@ApiModelProperty(value="조회수", example = "3", required = true)
@ApiModelProperty(value = "조회수", example = "3", required = true)
private int count;
@ApiModelProperty(value="좋아요 수", example = "-1", required = true)
private int liked;
@ApiModelProperty(value="릴리즈 노트 ID", example = "1", required = true)
@ApiModelProperty(value = "좋아요 수", example = "-1", required = true)
private Long liked;
@ApiModelProperty(value = "릴리즈 노트 ID", example = "1", required = true)
private Long releaseNoteId;
}
14 changes: 14 additions & 0 deletions src/main/java/com/swave/urnr/releasenote/service/LikedService.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
package com.swave.urnr.releasenote.service;

import com.swave.urnr.releasenote.responsedto.LikedCountResponseDTO;
import com.swave.urnr.util.http.HttpResponse;

import javax.servlet.http.HttpServletRequest;

public interface LikedService {
public HttpResponse createLiked(HttpServletRequest request, Long releaseNoteId);

public HttpResponse cancelLiked(HttpServletRequest request, Long releaseNodeId);

public LikedCountResponseDTO countLiked(Long releaseNodeId);
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,94 @@
package com.swave.urnr.releasenote.service;

import com.swave.urnr.releasenote.domain.Liked;
import com.swave.urnr.releasenote.domain.SeenCheck;
import com.swave.urnr.releasenote.repository.LikedRepository;
import com.swave.urnr.releasenote.repository.ReleaseNoteRepository;
import com.swave.urnr.releasenote.repository.SeenCheckRepository;
import com.swave.urnr.releasenote.responsedto.LikedCountResponseDTO;
import com.swave.urnr.user.domain.UserInProject;
import com.swave.urnr.util.http.HttpResponse;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.security.access.AccessDeniedException;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.EnableTransactionManagement;
import org.springframework.transaction.annotation.Transactional;

import javax.servlet.http.HttpServletRequest;
import java.util.NoSuchElementException;

@Service
@RequiredArgsConstructor
@Slf4j
@EnableTransactionManagement
public class LikedServiceImpl implements LikedService {

private final ReleaseNoteRepository releaseNoteRepository;
private final SeenCheckRepository seenCheckRepository;
private final LikedRepository likedRepository;

@Override
@Transactional
public HttpResponse createLiked(HttpServletRequest request, Long releaseNoteId){
UserInProject userInProject = releaseNoteRepository.findUserInProjectByUserIdAndReleaseNoteId((Long) request.getAttribute("id"), releaseNoteId);
SeenCheck seenCheck;

if(userInProject == null){
throw new AccessDeniedException("해당 프로젝트의 접근 권한이 없습니다.");
}else{
seenCheck = seenCheckRepository.findByUserInProjectIdAndReleaseNoteId(userInProject.getId(), releaseNoteId);
}

if(null != likedRepository.findBySeenCheck_Id(seenCheck.getId())){
throw new RuntimeException("이미 좋아요 한 기록이 있습니다.");
}

Liked liked = Liked.builder()
.isLiked(true)
.seenCheck(seenCheck)
.build();

likedRepository.saveAndFlush(liked);

return HttpResponse.builder()
.message("Liked Created")
.description("Liked ID : " + liked.getId() + " Created")
.build();
}

@Override
@Transactional
public HttpResponse cancelLiked(HttpServletRequest request, Long releaseNoteId){
UserInProject userInProject = releaseNoteRepository.findUserInProjectByUserIdAndReleaseNoteId((Long) request.getAttribute("id"), releaseNoteId);
SeenCheck seenCheck;

if(userInProject == null){
throw new AccessDeniedException("해당 프로젝트의 접근 권한이 없습니다.");
}else{
seenCheck = seenCheckRepository.findById(userInProject.getId())
.orElseThrow(NoSuchElementException::new);
}

Liked liked = likedRepository.findBySeenCheck_Id(seenCheck.getId());
if(null == liked){
throw new RuntimeException("좋아요 한 기록이 없습니다.");
}

liked.setIsLiked(false);

likedRepository.flush();

return HttpResponse.builder()
.message("Liked Cancelled")
.description("Liked ID : " + liked.getId() + " Cancelled")
.build();
}

@Override
public LikedCountResponseDTO countLiked(Long releaseNoteId){
LikedCountResponseDTO likedCountResponseDTO = new LikedCountResponseDTO();
likedCountResponseDTO.setLikedCount(likedRepository.countByLiked(releaseNoteId));
return likedCountResponseDTO;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,7 @@ public class ReleaseNoteServiceImpl implements ReleaseNoteService{
private final ChatGPTService chatGPTService;
private final SeenCheckService seenCheckService;
private final CommentService commentService;
private final LikedService likedService;


//todo 나중에 다른 쪽에서 구현이 끝나면 service로 갈아 끼울것
Expand Down Expand Up @@ -131,6 +132,9 @@ public ReleaseNoteContentResponseDTO loadReleaseNote(HttpServletRequest request,
ReleaseNoteContentResponseDTO releaseNoteContentResponseDTO = releaseNote.makeReleaseNoteContentDTO();
releaseNoteContentResponseDTO.setComment(commentContentList);

LikedCountResponseDTO likedCountResponseDTO = likedService.countLiked(releaseNoteId);
releaseNoteContentResponseDTO.setLiked(likedCountResponseDTO.getLikedCount());

releaseNote.addViewCount();
releaseNoteRepository.flush();

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,5 +9,5 @@
import com.swave.urnr.user.domain.UserInProject;

public interface SeenCheckService {
SeenCheck createSeenCheck(String username , ReleaseNote releaseNote, UserInProject userInProject);
public SeenCheck createSeenCheck(String username , ReleaseNote releaseNote, UserInProject userInProject);
}
Original file line number Diff line number Diff line change
@@ -1,13 +1,8 @@
package com.swave.urnr.releasenote.service;

import com.swave.urnr.releasenote.domain.BlockContext;
import com.swave.urnr.releasenote.domain.NoteBlock;
import com.swave.urnr.releasenote.domain.ReleaseNote;
import com.swave.urnr.releasenote.domain.SeenCheck;
import com.swave.urnr.releasenote.repository.BlockContextRepository;
import com.swave.urnr.releasenote.repository.SeenCheckRepository;
import com.swave.urnr.releasenote.requestdto.BlockContextCreateRequestDTO;
import com.swave.urnr.releasenote.requestdto.BlockContextUpdateRequestDTO;
import com.swave.urnr.user.domain.UserInProject;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
Expand Down Expand Up @@ -40,5 +35,4 @@ public SeenCheck createSeenCheck(String username , ReleaseNote releaseNote, User

return seenCheck;
}

}
15 changes: 3 additions & 12 deletions src/main/resources/application.properties
Original file line number Diff line number Diff line change
@@ -1,7 +1,5 @@
spring.jpa.properties.hibernate.format_sql = true

spring.jpa.hibernate.ddl-auto = none

spring.jpa.properties.hibernate.format_sql = true
spring.jpa.hibernate.ddl-auto = update
spring.jpa.generate-ddl = true
spring.jpa.database = mysql
spring.jpa.show-sql = true
Expand All @@ -16,11 +14,4 @@ spring.datasource.url = jdbc:mysql://localhost:3306/release_note\
spring.datasource.username = root
spring.datasource.password = admin

spring.mvc.pathmatch.matching-strategy = ant_path_matcher

server:
servlet:
encoding:
charset: UTF-8
enabled: true
force: true
spring.mvc.pathmatch.matching-strategy = ant_path_matcher
Loading

0 comments on commit 73c0fa0

Please sign in to comment.