Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@
import com.dnd.moddo.event.infrastructure.PaymentRequestRepository;
import com.dnd.moddo.event.presentation.response.PaymentRequestItemResponse;
import com.dnd.moddo.event.presentation.response.PaymentRequestsResponse;
import com.dnd.moddo.event.presentation.response.PaymentRequestSummaryResponse;

import lombok.RequiredArgsConstructor;

Expand Down Expand Up @@ -65,15 +66,13 @@ public boolean existsBySettlementId(Long settlementId) {
return paymentRequestRepository.existsBySettlementId(settlementId);
}

public Map<Long, Long> findPendingRequestIdByMemberId(Long settlementId) {
return paymentRequestRepository.findBySettlementIdAndStatus(settlementId, PaymentRequestStatus.PENDING)
public Map<Long, PaymentRequestSummaryResponse> findLatestRequestByMemberId(Long settlementId) {
return paymentRequestRepository.findBySettlementIdOrderByRequestedAtDesc(settlementId)
.stream()
.collect(Collectors.toMap(
PaymentRequest::getRequestMemberId,
PaymentRequest::getId,
(first, duplicate) -> {
throw new IllegalStateException("중복된 PENDING 입금 확인 요청이 존재합니다.");
}
PaymentRequestSummaryResponse::of,
(first, duplicate) -> first
));
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@
import com.dnd.moddo.event.presentation.response.MemberExpenseItemResponse;
import com.dnd.moddo.event.presentation.response.MemberExpenseResponse;
import com.dnd.moddo.event.presentation.response.MembersExpenseResponse;
import com.dnd.moddo.event.presentation.response.PaymentRequestSummaryResponse;

import lombok.RequiredArgsConstructor;

Expand All @@ -44,8 +45,8 @@ public List<MemberExpenseResponse> findAllByExpenseId(

public MembersExpenseResponse findMemberExpenseDetailsBySettlementId(Long settlementId, Long userId) {
Settlement settlement = settlementReader.read(settlementId);
Map<Long, Long> paymentRequestIdByMemberId = settlement.isWriter(userId)
? paymentRequestReader.findPendingRequestIdByMemberId(settlementId)
Map<Long, PaymentRequestSummaryResponse> paymentRequestByMemberId = settlement.isWriter(userId)
? paymentRequestReader.findLatestRequestByMemberId(settlementId)
: Map.of();

List<Member> members = memberReader.findAllBySettlementId(settlementId);
Expand All @@ -66,7 +67,7 @@ public MembersExpenseResponse findMemberExpenseDetailsBySettlementId(Long settle
key -> findMemberExpenseDetailByAppointmentMember(appointmentMemberById.get(key),
memberExpenses.get(key),
expenses,
paymentRequestIdByMemberId)
paymentRequestByMemberId)
)
.filter(Objects::nonNull)
.toList();
Expand All @@ -84,18 +85,18 @@ private Map<Long, Member> convertAppointmentMembersToMap(List<Member> members) {

private MemberExpenseItemResponse findMemberExpenseDetailByAppointmentMember(
Member member, List<MemberExpense> memberExpenses, List<Expense> expenses,
Map<Long, Long> paymentRequestIdByMemberId) {
Map<Long, PaymentRequestSummaryResponse> paymentRequestByMemberId) {

Long paymentRequestId = paymentRequestIdByMemberId.get(member.getId());
PaymentRequestSummaryResponse paymentRequest = paymentRequestByMemberId.get(member.getId());

if (memberExpenses == null) {
return MemberExpenseItemResponse.of(member, 0L, new ArrayList<>(), paymentRequestId);
return MemberExpenseItemResponse.of(member, 0L, new ArrayList<>(), paymentRequest);
}

List<MemberExpenseDetailResponse> memberExpenseDetails = mapToMemberExpenseDetails(memberExpenses, expenses);
Long totalAmount = calculateTotalAmount(memberExpenses);

return MemberExpenseItemResponse.of(member, totalAmount, memberExpenseDetails, paymentRequestId);
return MemberExpenseItemResponse.of(member, totalAmount, memberExpenseDetails, paymentRequest);
}

private Long calculateTotalAmount(List<MemberExpense> memberExpenses) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@
import com.dnd.moddo.event.presentation.response.SettlementHeaderResponse;
import com.dnd.moddo.event.presentation.response.SettlementListResponse;
import com.dnd.moddo.event.presentation.response.SettlementShareResponse;
import com.dnd.moddo.event.presentation.response.PaymentRequestSummaryResponse;

import lombok.RequiredArgsConstructor;

Expand All @@ -39,8 +40,9 @@ public SettlementDetailResponse findOne(Long settlementId, Long userId) {
Settlement settlement = settlementReader.read(settlementId);
settlementValidator.checkSettlementAuthor(settlement, userId);
List<Member> members = settlementReader.findBySettlement(settlementId);
Map<Long, Long> paymentRequestIdByMemberId = paymentRequestReader.findPendingRequestIdByMemberId(settlementId);
return SettlementDetailResponse.of(settlement, members, paymentRequestIdByMemberId);
Map<Long, PaymentRequestSummaryResponse> paymentRequestByMemberId =
paymentRequestReader.findLatestRequestByMemberId(settlementId);
return SettlementDetailResponse.of(settlement, members, paymentRequestByMemberId);
}

public SettlementHeaderResponse findBySettlementHeader(Long settlementId) {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,16 @@
package com.dnd.moddo.event.domain.paymentRequest;

import lombok.Getter;

@Getter
public enum PaymentRequestStatus {
PENDING, APPROVED, REJECTED
PENDING("확인중"),
APPROVED("승인완료"),
REJECTED("거절");

private final String label;

PaymentRequestStatus(String label) {
this.label = label;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -44,10 +44,7 @@ select count(pr) > 0
select pr
from PaymentRequest pr
where pr.settlement.id = :settlementId
and pr.status = :status
""")
List<PaymentRequest> findBySettlementIdAndStatus(
@Param("settlementId") Long settlementId,
@Param("status") PaymentRequestStatus status
);
order by pr.requestedAt desc, pr.id desc
""")
List<PaymentRequest> findBySettlementIdOrderByRequestedAtDesc(@Param("settlementId") Long settlementId);
}
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@

import com.dnd.moddo.event.domain.member.ExpenseRole;
import com.dnd.moddo.event.domain.member.Member;
import com.dnd.moddo.event.domain.paymentRequest.PaymentRequestStatus;

import lombok.Builder;

Expand All @@ -18,10 +19,12 @@ public record MemberExpenseItemResponse(
boolean isPaid,
LocalDateTime paidAt,
Long paymentRequestId,
PaymentRequestStatus paymentRequestStatus,
String paymentRequestStatusLabel,
List<MemberExpenseDetailResponse> expenses
) {
public static MemberExpenseItemResponse of(Member member, Long totalAmount,
List<MemberExpenseDetailResponse> expenses, Long paymentRequestId) {
List<MemberExpenseDetailResponse> expenses, PaymentRequestSummaryResponse paymentRequest) {
return MemberExpenseItemResponse.builder()
.id(member.getId())
.role(member.getRole())
Expand All @@ -30,7 +33,9 @@ public static MemberExpenseItemResponse of(Member member, Long totalAmount,
.profile(member.getProfileUrl())
.isPaid(member.isPaid())
.paidAt(member.getPaidAt())
.paymentRequestId(paymentRequestId)
.paymentRequestId(paymentRequest == null ? null : paymentRequest.id())
.paymentRequestStatus(paymentRequest == null ? null : paymentRequest.status())
.paymentRequestStatusLabel(paymentRequest == null ? null : paymentRequest.statusLabel())
.expenses(expenses).build();
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,8 @@ public record PaymentRequestResponse(
Long targetUserId,
LocalDateTime requestedAt,
LocalDateTime processedAt,
PaymentRequestStatus status
PaymentRequestStatus status,
String statusLabel
) {
public static PaymentRequestResponse of(PaymentRequest paymentRequest) {
return new PaymentRequestResponse(
Expand All @@ -22,7 +23,8 @@ public static PaymentRequestResponse of(PaymentRequest paymentRequest) {
paymentRequest.getTargetUserId(),
paymentRequest.getRequestedAt(),
paymentRequest.getProcessedAt(),
paymentRequest.getStatus()
paymentRequest.getStatus(),
paymentRequest.getStatus().getLabel()
);
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
package com.dnd.moddo.event.presentation.response;

import com.dnd.moddo.event.domain.paymentRequest.PaymentRequest;
import com.dnd.moddo.event.domain.paymentRequest.PaymentRequestStatus;

public record PaymentRequestSummaryResponse(
Long id,
PaymentRequestStatus status,
String statusLabel
) {
public static PaymentRequestSummaryResponse of(PaymentRequest paymentRequest) {
return new PaymentRequestSummaryResponse(
paymentRequest.getId(),
paymentRequest.getStatus(),
paymentRequest.getStatus().getLabel()
);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -19,10 +19,10 @@ public static SettlementDetailResponse of(Settlement settlement, List<Member> me
public static SettlementDetailResponse of(
Settlement settlement,
List<Member> members,
Map<Long, Long> paymentRequestIdByMemberId
Map<Long, PaymentRequestSummaryResponse> paymentRequestByMemberId
) {
List<SettlementMemberResponse> memberResponses = members.stream()
.map(member -> SettlementMemberResponse.of(member, paymentRequestIdByMemberId.get(member.getId())))
.map(member -> SettlementMemberResponse.of(member, paymentRequestByMemberId.get(member.getId())))
.collect(Collectors.toList());
return new SettlementDetailResponse(
settlement.getId(),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@

import com.dnd.moddo.event.domain.member.ExpenseRole;
import com.dnd.moddo.event.domain.member.Member;
import com.dnd.moddo.event.domain.paymentRequest.PaymentRequestStatus;

import lombok.Builder;

Expand All @@ -16,18 +17,22 @@ public record SettlementMemberResponse(
Long userId,
Boolean isPaid,
LocalDateTime paidAt,
Long paymentRequestId
Long paymentRequestId,
PaymentRequestStatus paymentRequestStatus,
String paymentRequestStatusLabel
) {

public static SettlementMemberResponse of(Member member, Long paymentRequestId) {
public static SettlementMemberResponse of(Member member, PaymentRequestSummaryResponse paymentRequest) {
return SettlementMemberResponse.builder()
.id(member.getId())
.name(member.getName())
.role(member.getRole())
.userId(member.getUserId())
.isPaid(member.isPaid())
.paidAt(member.getPaidAt())
.paymentRequestId(paymentRequestId)
.paymentRequestId(paymentRequest == null ? null : paymentRequest.id())
.paymentRequestStatus(paymentRequest == null ? null : paymentRequest.status())
.paymentRequestStatusLabel(paymentRequest == null ? null : paymentRequest.statusLabel())
.profile(member.getProfileUrl())
.build();
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@
import org.springframework.http.MediaType;

import com.dnd.moddo.auth.presentation.response.LoginUserInfo;
import com.dnd.moddo.event.domain.paymentRequest.PaymentRequestStatus;
import com.dnd.moddo.event.presentation.response.MemberExpenseDetailResponse;
import com.dnd.moddo.event.presentation.response.MemberExpenseItemResponse;
import com.dnd.moddo.event.presentation.response.MembersExpenseResponse;
Expand All @@ -31,11 +32,12 @@ void getMemberExpensesDetailsSuccess() throws Exception {
List.of(
new MemberExpenseItemResponse(1L, MANAGER, "김모또", 10000L,
"https://moddo-s3.s3.amazonaws.com/profile/MODDO.png", true, LocalDateTime.now(),
null, List.of(new MemberExpenseDetailResponse("카페", 10000L))
null, null, null, List.of(new MemberExpenseDetailResponse("카페", 10000L))
),
new MemberExpenseItemResponse(2L, PARTICIPANT, "군계란", 10000L,
"https://moddo-s3.s3.amazonaws.com/profile/1.png", false, null,
100L, List.of(new MemberExpenseDetailResponse("카페", 10000L))
100L, PaymentRequestStatus.APPROVED, "승인완료",
List.of(new MemberExpenseDetailResponse("카페", 10000L))
)
)
);
Expand All @@ -53,7 +55,9 @@ void getMemberExpensesDetailsSuccess() throws Exception {
.contentType(MediaType.APPLICATION_JSON))
.andExpect(status().isOk())
.andExpect(jsonPath("$.memberExpenses").isArray())
.andExpect(jsonPath("$.memberExpenses[1].paymentRequestId").value(100L));
.andExpect(jsonPath("$.memberExpenses[1].paymentRequestId").value(100L))
.andExpect(jsonPath("$.memberExpenses[1].paymentRequestStatus").value("APPROVED"))
.andExpect(jsonPath("$.memberExpenses[1].paymentRequestStatusLabel").value("승인완료"));

verify(querySettlementService, times(1)).findIdByCode(code);
verify(queryMemberExpenseService, times(1)).findMemberExpenseDetailsBySettlementId(groupId, 1L);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -25,9 +25,11 @@
import com.dnd.moddo.event.domain.member.ExpenseRole;
import com.dnd.moddo.event.domain.member.Member;
import com.dnd.moddo.event.domain.memberExpense.MemberExpense;
import com.dnd.moddo.event.domain.paymentRequest.PaymentRequestStatus;
import com.dnd.moddo.event.domain.settlement.Settlement;
import com.dnd.moddo.event.presentation.response.MemberExpenseResponse;
import com.dnd.moddo.event.presentation.response.MembersExpenseResponse;
import com.dnd.moddo.event.presentation.response.PaymentRequestSummaryResponse;

@ExtendWith(MockitoExtension.class)
class QueryMemberExpenseServiceTest {
Expand Down Expand Up @@ -125,7 +127,9 @@ void findMemberExpenseDetailsBySettlementId_Success() {
when(expense2.getId()).thenReturn(2L);

when(settlementReader.read(groupId)).thenReturn(mockSettlement);
when(paymentRequestReader.findPendingRequestIdByMemberId(groupId)).thenReturn(Map.of(2L, 100L));
when(paymentRequestReader.findLatestRequestByMemberId(groupId))
.thenReturn(Map.of(2L,
new PaymentRequestSummaryResponse(100L, PaymentRequestStatus.APPROVED, "승인완료")));
when(memberReader.findAllBySettlementId(eq(groupId))).thenReturn(members);
when(memberExpenseReader.findAllByAppointMemberIds(List.of(1L, 2L)))
.thenReturn(List.of(memberExpense1, memberExpense2));
Expand All @@ -139,10 +143,14 @@ void findMemberExpenseDetailsBySettlementId_Success() {
assertThat(response).isNotNull();
assertThat(response.memberExpenses()).hasSize(2);
assertThat(response.memberExpenses().get(0).paymentRequestId()).isNull();
assertThat(response.memberExpenses().get(0).paymentRequestStatus()).isNull();
assertThat(response.memberExpenses().get(0).paymentRequestStatusLabel()).isNull();
assertThat(response.memberExpenses().get(1).paymentRequestId()).isEqualTo(100L);
assertThat(response.memberExpenses().get(1).paymentRequestStatus()).isEqualTo(PaymentRequestStatus.APPROVED);
assertThat(response.memberExpenses().get(1).paymentRequestStatusLabel()).isEqualTo("승인완료");

verify(settlementReader, times(1)).read(groupId);
verify(paymentRequestReader, times(1)).findPendingRequestIdByMemberId(groupId);
verify(paymentRequestReader, times(1)).findLatestRequestByMemberId(groupId);
verify(memberReader, times(1)).findAllBySettlementId(groupId);
verify(memberExpenseReader, times(1)).findAllByAppointMemberIds(anyList());
verify(expenseReader, times(1)).findAllBySettlementId(groupId);
Expand Down Expand Up @@ -170,9 +178,11 @@ void findMemberExpenseDetailsBySettlementId_Success_WhenNotManager() {
assertThat(response).isNotNull();
assertThat(response.memberExpenses()).hasSize(1);
assertThat(response.memberExpenses().get(0).paymentRequestId()).isNull();
assertThat(response.memberExpenses().get(0).paymentRequestStatus()).isNull();
assertThat(response.memberExpenses().get(0).paymentRequestStatusLabel()).isNull();

verify(settlementReader, times(1)).read(groupId);
verify(paymentRequestReader, never()).findPendingRequestIdByMemberId(anyLong());
verify(paymentRequestReader, never()).findLatestRequestByMemberId(anyLong());
verify(memberReader, times(1)).findAllBySettlementId(groupId);
}

Expand Down
Loading
Loading