Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[OING-304] feature: 회원 생존신고 게시글 업로드 여부 / 가족 미션 참여 가능 여부 확인 API 구현 #240

Merged
merged 10 commits into from
Apr 24, 2024
Original file line number Diff line number Diff line change
Expand Up @@ -28,13 +28,12 @@ public class MainViewController implements MainViewApi {
private final MemberPickService memberPickService;
private final MemberBridge memberBridge;
private final MissionBridge missionBridge;
private final PostController postController;

private static final int PAGE_FETCH_SIZE = 1000;

@Override
public DaytimePageResponse getDaytimePage(
boolean isMissionUnlocked,
boolean isMeUploadedToday,
String loginMemberId
) {
String familyId = memberBridge.getFamilyIdByMemberId(loginMemberId);
Expand Down Expand Up @@ -67,6 +66,10 @@ public DaytimePageResponse getDaytimePage(

String todayMissionId = missionBridge.getTodayMissionId();
String dailyMissionContent = missionBridge.getContentByMissionId(todayMissionId);
boolean isMissionUnlocked = postController.getMissionAvailableStatus(loginMemberId, loginMemberId, familyId)
.isMissionUnlocked();
boolean isMeUploadedToday = postController.getSurvivalUploadStatus(loginMemberId, loginMemberId, familyId)
.isMeUploadedToday();


return new DaytimePageResponse(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -116,6 +116,28 @@ public boolean existsByMemberIdAndFamilyIdAndTypeAndCreatedAt(String memberId, S
.fetchFirst() != null;
}

@Override
public boolean isCreatedSurvivalPostByMajority(LocalDate date, String familyId) {
long totalFamilyMembers = queryFactory
.select(member.count())
.from(member)
.where(member.familyId.eq(familyId)
.and(member.deletedAt.isNull()))
.fetchFirst();

long survivalPostCount = queryFactory
.select(post.count())
.from(post)
.where(
post.familyId.eq(familyId),
post.type.eq(PostType.SURVIVAL),
dateExpr(post.createdAt).eq(date)
)
.fetchFirst();

return survivalPostCount >= totalFamilyMembers / 2;
}

private DateTimeTemplate<LocalDate> dateExpr(DateTimePath<LocalDateTime> localDateTime) {
return Expressions.dateTimeTemplate(LocalDate.class, "DATE({0})", localDateTime);
}
Expand Down
10 changes: 0 additions & 10 deletions gateway/src/main/java/com/oing/restapi/MainViewApi.java
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,6 @@
import io.swagger.v3.oas.annotations.tags.Tag;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;

/**
Expand All @@ -27,15 +26,6 @@ public interface MainViewApi {
@Operation(summary = "주간의 메인 페이지 조회")
@GetMapping("/daytime-page")
DaytimePageResponse getDaytimePage(

@RequestParam(required = false, defaultValue = "true")
@Parameter(description = "(디버그용) 미션 해금 여부 조작 필드", example = "true")
boolean isMissionUnlocked,

@RequestParam(required = false, defaultValue = "true")
@Parameter(description = "(디버그용) 오늘 나 업로드 여부 조작 필드", example = "true")
boolean isMeUploadedToday,

@Parameter(hidden = true)
@LoginMemberId
String loginMemberId
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -127,4 +127,30 @@ void setup() {
// then
assertThat(exists).isFalse();
}

@Test
void 미션_키_획득한_날짜에_가족의_미션_키_획득_여부를_조회한다() {
// given
String familyId = testMember1.getFamilyId();
LocalDate today = LocalDate.of(2023, 11, 1);

// when
boolean exists = postRepositoryCustomImpl.isCreatedSurvivalPostByMajority(today, familyId);

// then
assertThat(exists).isTrue();
}

@Test
void 미션_키_획득하지_못한_날짜에_가족의_미션_키_획득_여부를_조회한다() {
// given
String familyId = testMember1.getFamilyId();
LocalDate today = LocalDate.of(2024, 4, 1);

// when
boolean exists = postRepositoryCustomImpl.isCreatedSurvivalPostByMajority(today, familyId);

// then
assertThat(exists).isFalse();
}
}
38 changes: 38 additions & 0 deletions gateway/src/test/java/com/oing/restapi/PostApiTest.java
Original file line number Diff line number Diff line change
Expand Up @@ -148,4 +148,42 @@ void setUp() {
.andExpect(jsonPath("$.results[0].authorId").value(TEST_MEMBER1_ID))
.andExpect(jsonPath("$.results[0].content").value("content"));
}

@Test
void 회원_생존신고_게시글_업로드_여부_조회_테스트() throws Exception {
//given
postRepository.save(new Post(TEST_POST_ID, TEST_MEMBER1_ID, TEST_FAMILY_ID, PostType.SURVIVAL, "img", "img",
"content"));

//when
ResultActions resultActions = mockMvc.perform(
get("/v1/posts/{memberId}/survival-uploaded", TEST_MEMBER1_ID)
.header("X-AUTH-TOKEN", TEST_MEMBER1_TOKEN)
.contentType(MediaType.APPLICATION_JSON)
);

//then
resultActions
.andExpect(status().isOk())
.andExpect(jsonPath("$.isMeUploadedToday").value(true));
}

@Test
void 해당_가족의_미션_키_획득_여부_조회_테스트() throws Exception {
//given
postRepository.save(new Post(TEST_POST_ID, TEST_MEMBER1_ID, TEST_FAMILY_ID, PostType.SURVIVAL, "img", "img",
"content"));

//when
ResultActions resultActions = mockMvc.perform(
get("/v1/posts/{memberId}/mission-available", TEST_MEMBER1_ID)
.header("X-AUTH-TOKEN", TEST_MEMBER1_TOKEN)
.contentType(MediaType.APPLICATION_JSON)
);

//then
resultActions
.andExpect(status().isOk())
.andExpect(jsonPath("$.isMissionUnlocked").value(true));
}
}
16 changes: 8 additions & 8 deletions post/src/main/java/com/oing/controller/PostController.java
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@
import org.springframework.stereotype.Controller;

import java.time.LocalDate;
import java.time.ZonedDateTime;

/**
* no5ing-server
Expand Down Expand Up @@ -91,22 +92,21 @@ public PostResponse getPost(String postId, String loginMemberId) {
}

@Override
public SurvivalUploadStatusResponse getSurvivalUploadStatus(String memberId, String loginMemberId, boolean valid) {
public SurvivalUploadStatusResponse getSurvivalUploadStatus(String memberId, String loginMemberId, String loginFamilyId) {
validateMemberId(loginMemberId, memberId);
// TODO: 추후 valid 파라미터 삭제
// TODO: 해당 회원이 생존신고 글을 올렸는지 검증 로직 추가
if (valid) {

if (postService.existsByMemberIdAndFamilyIdAndTypeAndCreatedAt(memberId, loginFamilyId, PostType.SURVIVAL, LocalDate.now())) {
return new SurvivalUploadStatusResponse(true);
}
return new SurvivalUploadStatusResponse(false);
}

@Override
public MissionAvailableStatusResponse getMissionAvailableStatus(String memberId, String loginMemberId, boolean valid) {
public MissionAvailableStatusResponse getMissionAvailableStatus(String memberId, String loginMemberId, String loginFamilyId) {
validateMemberId(loginMemberId, memberId);
// TODO: 추후 valid 파라미터 삭제
// TODO: 해당 회원이 미션에 참여 가능한 회원인지 검증 로직 추가
if (valid) {
LocalDate today = ZonedDateTime.now().toLocalDate();

if (postService.isCreatedSurvivalPostByMajority(today, loginFamilyId)) {
return new MissionAvailableStatusResponse(true);
}
return new MissionAvailableStatusResponse(false);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,9 @@

import io.swagger.v3.oas.annotations.media.Schema;

@Schema(description = "회원 미션 참여 가능 여부 응답")
@Schema(description = "가족 미션 참여 가능 (미션 키) 여부 응답")
public record MissionAvailableStatusResponse(
@Schema(description = "회원 미션 참여 가능 여부", example = "true")
boolean isAvailable
@Schema(description = "가족 미션 참여 가능 (미션 키) 여부", example = "true")
boolean isMissionUnlocked
) {
}
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,6 @@
@Schema(description = "회원 생존신고 게시글 업로드 여부 응답")
public record SurvivalUploadStatusResponse(
@Schema(description = "회원 생존신고 게시글 업로드 여부", example = "true")
boolean isValid
boolean isMeUploadedToday
) {
}
Original file line number Diff line number Diff line change
Expand Up @@ -22,4 +22,5 @@ QueryResults<Post> searchPosts(int page, int size, LocalDate date, String member

boolean existsByMemberIdAndFamilyIdAndTypeAndCreatedAt(String memberId, String familyId, PostType type, LocalDate postDate);

boolean isCreatedSurvivalPostByMajority(LocalDate date, String familyId);
}
12 changes: 6 additions & 6 deletions post/src/main/java/com/oing/restapi/PostApi.java
Original file line number Diff line number Diff line change
Expand Up @@ -125,9 +125,9 @@ SurvivalUploadStatusResponse getSurvivalUploadStatus(
@LoginMemberId
String loginMemberId,

@RequestParam
@Parameter(description = "응답 값 조작 필드", example = "true")
boolean valid
@Parameter(hidden = true)
@LoginFamilyId
String loginFamilyId
);

@Operation(summary = "회원 미션 참여 가능 여부 응답 조회", description = "회원 미션 참여 가능 여부를 조회합니다.")
Expand All @@ -141,8 +141,8 @@ MissionAvailableStatusResponse getMissionAvailableStatus(
@LoginMemberId
String loginMemberId,

@RequestParam
@Parameter(description = "응답 값 조작 필드", example = "true")
boolean valid
@Parameter(hidden = true)
@LoginFamilyId
String loginFamilyId
);
}
4 changes: 4 additions & 0 deletions post/src/main/java/com/oing/service/PostService.java
Original file line number Diff line number Diff line change
Expand Up @@ -160,4 +160,8 @@ public boolean existsByFamilyIdAndCreatedAt(String familyId, LocalDate postDate)
public boolean existsByMemberIdAndFamilyIdAndTypeAndCreatedAt(String memberId, String familyId, PostType type, LocalDate postDate) {
return postRepository.existsByMemberIdAndFamilyIdAndTypeAndCreatedAt(memberId, familyId, type, postDate);
}

public boolean isCreatedSurvivalPostByMajority(LocalDate date, String familyId) {
return postRepository.isCreatedSurvivalPostByMajority(date, familyId);
}
}
Loading