Skip to content

Commit

Permalink
Merge pull request #120 from modu-menu/develop
Browse files Browse the repository at this point in the history
main에 develop merge
  • Loading branch information
eelseungmin authored Jun 11, 2024
2 parents 5edafbc + a5c26cc commit 5015e60
Show file tree
Hide file tree
Showing 24 changed files with 580 additions and 19 deletions.
11 changes: 9 additions & 2 deletions build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -73,6 +73,12 @@ jacocoTestReport {
csv.required.set(false)
}

// QueryDSL QDomain 제외시키기
def QDomains = []
for (qPattern in '**/QA'..'**/QZ') {
QDomains.add(qPattern + '*')
}

afterEvaluate {
classDirectories.setFrom(
files(classDirectories.files.collect {
Expand All @@ -87,8 +93,9 @@ jacocoTestReport {
"**/*Filter*",
"**/converter/**",
"**/HealthCheckController.class",
"**/oauth2/**"
])
"**/oauth2/**",
"**/interceptor/**"
] + QDomains)
})
)
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,4 +23,13 @@ select count(*)
where c.user.id = :userId and c.voteItem.id in :voteItemIds
""")
Optional<Choice> findByUserIdAndVoteItemIds(@Param("userId") Long userId, @Param("voteItemIds") List<Long> voteItemIds);

@Query("""
select c
from Choice c
join c.voteItem vi
join vi.vote v
where v.id = :voteId
""")
List<Choice> findByVoteId(@Param("voteId") Long voteId);
}
Original file line number Diff line number Diff line change
@@ -1,10 +1,12 @@
package modu.menu.participant.repository;

import modu.menu.participant.domain.Participant;
import modu.menu.user.domain.User;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.data.jpa.repository.Query;
import org.springframework.data.repository.query.Param;

import java.util.List;
import java.util.Optional;

public interface ParticipantRepository extends JpaRepository<Participant, Long> {
Expand All @@ -22,4 +24,12 @@ public interface ParticipantRepository extends JpaRepository<Participant, Long>
where p.user.id = :userId and p.vote.id = :voteId
""")
Optional<Participant> findByUserIdAndVoteId(@Param("userId") Long userId, @Param("voteId") Long voteId);

@Query("""
select u
from Participant p
join p.user u
where p.vote.id = :voteId
""")
List<User> findUserByVoteId(@Param("voteId") Long voteId);
}
15 changes: 15 additions & 0 deletions src/main/java/modu/menu/vote/api/VoteController.java
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@
import modu.menu.vote.api.request.SaveVoteRequest;
import modu.menu.vote.api.request.VoteRequest;
import modu.menu.vote.api.request.VoteResultRequest;
import modu.menu.vote.api.response.TurnoutResponse;
import modu.menu.vote.api.response.VoteResultResponse;
import modu.menu.vote.service.VoteService;
import org.springframework.http.ResponseEntity;
Expand Down Expand Up @@ -112,6 +113,20 @@ public ResponseEntity<ApiSuccessResponse> vote(
.body(new ApiSuccessResponse<>());
}

@Operation(summary = "투표율 조회", description = """
투표에 초대된 사람들을 기준으로 투표율과 각 사람 별 투표 여부를 조회합니다.
""")
@SecurityRequirement(name = "Authorization")
@GetMapping("/api/vote/{voteId}/turnout")
public ResponseEntity<ApiSuccessResponse<TurnoutResponse>> getTurnout(
@Positive(message = "voteId는 양수여야 합니다.") @PathVariable("voteId") Long voteId
) {
TurnoutResponse response = voteService.getTurnout(voteId);

return ResponseEntity.ok()
.body(new ApiSuccessResponse<>(response));
}

/**
* 회원의 위도와 경도를 외부에 노출해선 안 된다고 판단하여
* HTTPS로 통신하는 점을 이용해 RequestBody에 위치 데이터를 담아서 요청하도록 설계
Expand Down
22 changes: 22 additions & 0 deletions src/main/java/modu/menu/vote/api/response/TurnoutResponse.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
package modu.menu.vote.api.response;

import io.swagger.v3.oas.annotations.media.Schema;
import lombok.AllArgsConstructor;
import lombok.Getter;
import lombok.NoArgsConstructor;
import modu.menu.vote.service.dto.IsVoteServiceResponse;

import java.util.List;

@Schema(description = "투표율 조회 응답 DTO")
@Getter
@NoArgsConstructor
@AllArgsConstructor
public class TurnoutResponse {

@Schema(description = "투표율", example = "30%")
private String turnout;

@Schema(description = "투표 여부 목록")
private List<IsVoteServiceResponse> participants;
}
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@

import java.util.List;

@Schema(description = "투표 결과 조회 DTO")
@Schema(description = "투표 결과 조회 응답 DTO")
@Getter
@NoArgsConstructor
@AllArgsConstructor
Expand Down
40 changes: 40 additions & 0 deletions src/main/java/modu/menu/vote/service/VoteService.java
Original file line number Diff line number Diff line change
Expand Up @@ -21,16 +21,19 @@
import modu.menu.vote.api.request.SaveVoteRequest;
import modu.menu.vote.api.request.VoteRequest;
import modu.menu.vote.api.request.VoteResultRequest;
import modu.menu.vote.api.response.TurnoutResponse;
import modu.menu.vote.api.response.VoteResultResponse;
import modu.menu.vote.domain.Vote;
import modu.menu.vote.domain.VoteStatus;
import modu.menu.vote.repository.VoteRepository;
import modu.menu.vote.service.dto.IsVoteServiceResponse;
import modu.menu.vote.service.dto.VoteResultServiceResponse;
import modu.menu.voteItem.domain.VoteItem;
import modu.menu.voteItem.repository.VoteItemRepository;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.Optional;
Expand Down Expand Up @@ -182,6 +185,43 @@ private VoteItem findSatisfiedVoteItem(VoteRequest voteRequest, List<VoteItem> v
.orElseThrow(() -> new Exception400(String.valueOf(voteRequest.getPlaceId()), ErrorMessage.NOT_EXIST_PLACE_IN_VOTE.getValue()));
}

// 투표율 조회
public TurnoutResponse getTurnout(Long voteId) {

voteRepository.findById(voteId).orElseThrow(
() -> new Exception404(ErrorMessage.NOT_EXIST_VOTE)
);

List<User> participants = participantRepository.findUserByVoteId(voteId);
if (participants.isEmpty()) {
return null;
}

List<Choice> choices = choiceRepository.findByVoteId(voteId);
List<IsVoteServiceResponse> list = new ArrayList<>();
int count = 0; // 투표한 사람의 인원 수
// Stream 내부에서 final이 아닌 지역변수를 사용할 수 없으므로 아래와 같이 for-each로 대체
for (User participant : participants) {
boolean isVote = false;
for (Choice choice : choices) {
if (choice.getUser().getId().equals(participant.getId())) {
count++;
isVote = true;
break;
}
}
list.add(IsVoteServiceResponse.builder()
.name(participant.getName())
.isVote(isVote)
.build());
}

return new TurnoutResponse(
Math.round((double) count / participants.size() * 100) + "%",
list
);
}

// TODO 투표 조회 API에서 해당 유저의 투표 여부를 변수로 같이 보내줘야 한다.
// 투표 결과 조회
public VoteResultResponse getResult(Long voteId, VoteResultRequest voteResultRequest) {
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
package modu.menu.vote.service.dto;

import io.swagger.v3.oas.annotations.media.Schema;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Getter;
import lombok.NoArgsConstructor;

@Schema(description = "투표 여부 DTO")
@Builder
@Getter
@AllArgsConstructor
@NoArgsConstructor
public class IsVoteServiceResponse {

@Schema(description = "투표자 이름", example = "이승민")
private String name;

@Schema(name = "투표 여부", examples = "true")
private Boolean isVote;
}
Loading

0 comments on commit 5015e60

Please sign in to comment.