FINERACT-2058: loan can be marked as fraud in any status

This commit is contained in:
taskain7
2024-03-01 12:06:43 +01:00
committed by Adam Saghy
parent ef1bcda368
commit 49b3c014ef
3 changed files with 82 additions and 81 deletions
@@ -2550,11 +2550,6 @@ public class LoanWritePlatformServiceJpaRepositoryImpl implements LoanWritePlatf
Loan loan = this.loanAssembler.assembleFrom(loanId); Loan loan = this.loanAssembler.assembleFrom(loanId);
final Map<String, Object> changes = new LinkedHashMap<>(); final Map<String, Object> changes = new LinkedHashMap<>();
if (loan.isApproved() || loan.isSubmittedAndPendingApproval()) {
throw new GeneralPlatformDomainRuleException("error.msg.loan.mark.as.fraud.not.allowed",
"Loan Id: " + loanId + " mark as fraud is not allowed as loan status is not active", loan.getStatus().getCode());
}
final boolean fraud = command.booleanPrimitiveValueOfParameterNamed(LoanApiConstants.FRAUD_ATTRIBUTE_NAME); final boolean fraud = command.booleanPrimitiveValueOfParameterNamed(LoanApiConstants.FRAUD_ATTRIBUTE_NAME);
if (loan.isFraud() != fraud) { if (loan.isFraud() != fraud) {
loan.markAsFraud(fraud); loan.markAsFraud(fraud);
@@ -401,6 +401,10 @@ public abstract class BaseLoanIntegrationTest {
.transactionAmount(amount).locale("en")); .transactionAmount(amount).locale("en"));
} }
protected void undoDisbursement(Integer loanId) {
loanTransactionHelper.undoDisbursal(loanId);
}
protected void verifyJournalEntries(Long loanId, Journal... entries) { protected void verifyJournalEntries(Long loanId, Journal... entries) {
GetJournalEntriesTransactionIdResponse journalEntriesForLoan = journalEntryHelper.getJournalEntriesForLoan(loanId); GetJournalEntriesTransactionIdResponse journalEntriesForLoan = journalEntryHelper.getJournalEntriesForLoan(loanId);
Assertions.assertEquals(entries.length, journalEntriesForLoan.getPageItems().size()); Assertions.assertEquals(entries.length, journalEntriesForLoan.getPageItems().size());
@@ -21,63 +21,50 @@ package org.apache.fineract.integrationtests;
import static org.junit.jupiter.api.Assertions.assertEquals; import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.jupiter.api.Assertions.assertNotNull; import static org.junit.jupiter.api.Assertions.assertNotNull;
import io.restassured.builder.RequestSpecBuilder; import java.math.BigDecimal;
import io.restassured.builder.ResponseSpecBuilder;
import io.restassured.http.ContentType;
import io.restassured.specification.RequestSpecification;
import io.restassured.specification.ResponseSpecification;
import java.time.LocalDate; import java.time.LocalDate;
import java.util.HashMap;
import lombok.extern.slf4j.Slf4j; import lombok.extern.slf4j.Slf4j;
import org.apache.fineract.client.models.GetLoanProductsProductIdResponse;
import org.apache.fineract.client.models.GetLoansLoanIdResponse; import org.apache.fineract.client.models.GetLoansLoanIdResponse;
import org.apache.fineract.client.models.PostLoanProductsRequest;
import org.apache.fineract.client.models.PostLoanProductsResponse;
import org.apache.fineract.client.models.PostLoansLoanIdResponse;
import org.apache.fineract.client.models.PostLoansResponse;
import org.apache.fineract.client.models.PutLoansLoanIdResponse; import org.apache.fineract.client.models.PutLoansLoanIdResponse;
import org.apache.fineract.infrastructure.businessdate.domain.BusinessDateType;
import org.apache.fineract.integrationtests.common.BusinessDateHelper;
import org.apache.fineract.integrationtests.common.ClientHelper; import org.apache.fineract.integrationtests.common.ClientHelper;
import org.apache.fineract.integrationtests.common.GlobalConfigurationHelper;
import org.apache.fineract.integrationtests.common.Utils; import org.apache.fineract.integrationtests.common.Utils;
import org.apache.fineract.integrationtests.common.loans.LoanApplicationTestBuilder;
import org.apache.fineract.integrationtests.common.loans.LoanProductTestBuilder;
import org.apache.fineract.integrationtests.common.loans.LoanTestLifecycleExtension; import org.apache.fineract.integrationtests.common.loans.LoanTestLifecycleExtension;
import org.apache.fineract.integrationtests.common.loans.LoanTransactionHelper;
import org.junit.jupiter.api.BeforeEach; import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Test; import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.extension.ExtendWith; import org.junit.jupiter.api.extension.ExtendWith;
@Slf4j @Slf4j
@ExtendWith(LoanTestLifecycleExtension.class) @ExtendWith(LoanTestLifecycleExtension.class)
public class LoanAccountFraudTest { public class LoanAccountFraudTest extends BaseLoanIntegrationTest {
private ResponseSpecification responseSpec; private static final double AMOUNT = 100.0;
private ResponseSpecification responseSpecError; private static final String COMMAND = "markAsFraud";
private RequestSpecification requestSpec;
private LoanTransactionHelper loanTransactionHelper;
private final String amountVal = "1000";
private LocalDate todaysDate; private LocalDate todaysDate;
private String operationDate; private String operationDate;
@BeforeEach @BeforeEach
public void setup() { public void setup() {
Utils.initializeRESTAssured(); Utils.initializeRESTAssured();
this.requestSpec = new RequestSpecBuilder().setContentType(ContentType.JSON).build();
this.requestSpec.header("Authorization", "Basic " + Utils.loginIntoServerAndGetBase64EncodedAuthenticationKey());
this.responseSpec = new ResponseSpecBuilder().expectStatusCode(200).build();
this.responseSpecError = new ResponseSpecBuilder().expectStatusCode(403).build();
this.loanTransactionHelper = new LoanTransactionHelper(this.requestSpec, this.responseSpec);
this.todaysDate = Utils.getLocalDateOfTenant(); this.todaysDate = Utils.getLocalDateOfTenant();
this.operationDate = Utils.dateFormatter.format(this.todaysDate); this.operationDate = Utils.dateFormatter.format(this.todaysDate);
} }
@Test @Test
public void testMarkLoanAsFraud() { public void testMarkLoanAsFraud() {
try { runAt(operationDate, () -> {
GlobalConfigurationHelper.updateIsBusinessDateEnabled(requestSpec, responseSpec, Boolean.TRUE);
BusinessDateHelper.updateBusinessDate(requestSpec, responseSpec, BusinessDateType.BUSINESS_DATE, todaysDate); final Long clientId = clientHelper.createClient(ClientHelper.defaultClientCreationRequest()).getClientId();
final String command = "markAsFraud";
// Client and Loan account creation PostLoanProductsRequest loanProductsRequest = createOnePeriod30DaysLongNoInterestPeriodicAccrualProduct();
final Integer loanId = createAccounts(15, 1); PostLoanProductsResponse loanProductResponse = loanProductHelper.createLoanProduct(loanProductsRequest);
PostLoansResponse postLoansResponse = loanTransactionHelper
.applyLoan(applyLoanRequest(clientId, loanProductResponse.getResourceId(), operationDate, AMOUNT, 1));
Integer loanId = postLoansResponse.getLoanId().intValue();
GetLoansLoanIdResponse getLoansLoanIdResponse = loanTransactionHelper.getLoan(requestSpec, responseSpec, loanId); GetLoansLoanIdResponse getLoansLoanIdResponse = loanTransactionHelper.getLoan(requestSpec, responseSpec, loanId);
assertNotNull(getLoansLoanIdResponse); assertNotNull(getLoansLoanIdResponse);
@@ -87,16 +74,46 @@ public class LoanAccountFraudTest {
assertEquals(Boolean.FALSE, getLoansLoanIdResponse.getFraud()); assertEquals(Boolean.FALSE, getLoansLoanIdResponse.getFraud());
String payload = loanTransactionHelper.getLoanFraudPayloadAsJSON("fraud", "true"); String payload = loanTransactionHelper.getLoanFraudPayloadAsJSON("fraud", "true");
// Send the request, not expecting any errors (because only open loan restriction removed) PutLoansLoanIdResponse putLoansLoanIdResponse = loanTransactionHelper.modifyLoanCommand(loanId, COMMAND, payload, responseSpec);
PutLoansLoanIdResponse putLoansLoanIdResponse = loanTransactionHelper.modifyLoanCommand(loanId, command, payload, assertNotNull(putLoansLoanIdResponse);
this.responseSpecError);
getLoansLoanIdResponse = loanTransactionHelper.getLoan(requestSpec, responseSpec, loanId);
assertNotNull(getLoansLoanIdResponse);
assertNotNull(getLoansLoanIdResponse.getFraud());
assertEquals(Boolean.TRUE, getLoansLoanIdResponse.getFraud());
String statusCode = getLoansLoanIdResponse.getStatus().getCode(); String statusCode = getLoansLoanIdResponse.getStatus().getCode();
log.info("Loan with Id {} is with Status {}", getLoansLoanIdResponse.getId(), statusCode); log.info("Loan with Id {} is with Status {}", getLoansLoanIdResponse.getId(), statusCode);
payload = loanTransactionHelper.getLoanFraudPayloadAsJSON("fraud", "false");
putLoansLoanIdResponse = loanTransactionHelper.modifyLoanCommand(loanId, COMMAND, payload, responseSpec);
assertNotNull(putLoansLoanIdResponse);
getLoansLoanIdResponse = loanTransactionHelper.getLoan(requestSpec, responseSpec, loanId);
assertNotNull(getLoansLoanIdResponse);
assertNotNull(getLoansLoanIdResponse.getFraud());
assertEquals(Boolean.FALSE, getLoansLoanIdResponse.getFraud());
statusCode = getLoansLoanIdResponse.getStatus().getCode();
log.info("Loan with Id {} is with Status {}", getLoansLoanIdResponse.getId(), statusCode);
// Approve the Loan active // Approve the Loan active
loanTransactionHelper.approveLoan(operationDate, this.amountVal, loanId, null); PostLoansLoanIdResponse approvedLoanResult = loanTransactionHelper.approveLoan(postLoansResponse.getResourceId(),
putLoansLoanIdResponse = loanTransactionHelper.modifyLoanCommand(loanId, command, payload, this.responseSpecError); approveLoanRequest(AMOUNT, operationDate));
assertNotNull(approvedLoanResult);
payload = loanTransactionHelper.getLoanFraudPayloadAsJSON("fraud", "true");
putLoansLoanIdResponse = loanTransactionHelper.modifyLoanCommand(loanId, COMMAND, payload, responseSpec);
assertNotNull(putLoansLoanIdResponse);
getLoansLoanIdResponse = loanTransactionHelper.getLoan(requestSpec, responseSpec, loanId);
assertNotNull(getLoansLoanIdResponse);
assertNotNull(getLoansLoanIdResponse.getFraud());
assertEquals(Boolean.TRUE, getLoansLoanIdResponse.getFraud());
statusCode = getLoansLoanIdResponse.getStatus().getCode();
log.info("Loan with Id {} is with Status {}", getLoansLoanIdResponse.getId(), statusCode);
payload = loanTransactionHelper.getLoanFraudPayloadAsJSON("fraud", "false");
putLoansLoanIdResponse = loanTransactionHelper.modifyLoanCommand(loanId, COMMAND, payload, responseSpec);
assertNotNull(putLoansLoanIdResponse);
// Default values Not Null and False // Default values Not Null and False
getLoansLoanIdResponse = loanTransactionHelper.getLoan(requestSpec, responseSpec, loanId); getLoansLoanIdResponse = loanTransactionHelper.getLoan(requestSpec, responseSpec, loanId);
@@ -106,10 +123,11 @@ public class LoanAccountFraudTest {
statusCode = getLoansLoanIdResponse.getStatus().getCode(); statusCode = getLoansLoanIdResponse.getStatus().getCode();
log.info("Loan with Id {} is with Status {}", getLoansLoanIdResponse.getId(), statusCode); log.info("Loan with Id {} is with Status {}", getLoansLoanIdResponse.getId(), statusCode);
loanTransactionHelper.disburseLoanWithNetDisbursalAmount(operationDate, loanId, this.amountVal); disburseLoan(loanId.longValue(), BigDecimal.valueOf(AMOUNT), operationDate);
// Mark On the Fraud // Mark On the Fraud
putLoansLoanIdResponse = loanTransactionHelper.modifyLoanCommand(loanId, command, payload, this.responseSpec); payload = loanTransactionHelper.getLoanFraudPayloadAsJSON("fraud", "true");
putLoansLoanIdResponse = loanTransactionHelper.modifyLoanCommand(loanId, COMMAND, payload, responseSpec);
assertNotNull(putLoansLoanIdResponse); assertNotNull(putLoansLoanIdResponse);
getLoansLoanIdResponse = loanTransactionHelper.getLoan(requestSpec, responseSpec, loanId); getLoansLoanIdResponse = loanTransactionHelper.getLoan(requestSpec, responseSpec, loanId);
@@ -119,49 +137,33 @@ public class LoanAccountFraudTest {
// Mark Off the Fraud // Mark Off the Fraud
payload = loanTransactionHelper.getLoanFraudPayloadAsJSON("fraud", "false"); payload = loanTransactionHelper.getLoanFraudPayloadAsJSON("fraud", "false");
putLoansLoanIdResponse = loanTransactionHelper.modifyLoanCommand(loanId, command, payload, this.responseSpec); putLoansLoanIdResponse = loanTransactionHelper.modifyLoanCommand(loanId, COMMAND, payload, this.responseSpec);
assertNotNull(putLoansLoanIdResponse); assertNotNull(putLoansLoanIdResponse);
getLoansLoanIdResponse = loanTransactionHelper.getLoan(requestSpec, responseSpec, loanId); getLoansLoanIdResponse = loanTransactionHelper.getLoan(requestSpec, responseSpec, loanId);
assertNotNull(getLoansLoanIdResponse); assertNotNull(getLoansLoanIdResponse);
assertNotNull(getLoansLoanIdResponse.getFraud()); assertNotNull(getLoansLoanIdResponse.getFraud());
assertEquals(Boolean.FALSE, getLoansLoanIdResponse.getFraud()); assertEquals(Boolean.FALSE, getLoansLoanIdResponse.getFraud());
} finally {
GlobalConfigurationHelper.updateIsBusinessDateEnabled(requestSpec, responseSpec, Boolean.FALSE); payload = loanTransactionHelper.getLoanFraudPayloadAsJSON("fraud", "true");
} putLoansLoanIdResponse = loanTransactionHelper.modifyLoanCommand(loanId, COMMAND, payload, responseSpec);
assertNotNull(putLoansLoanIdResponse);
getLoansLoanIdResponse = loanTransactionHelper.getLoan(requestSpec, responseSpec, loanId);
assertNotNull(getLoansLoanIdResponse);
assertNotNull(getLoansLoanIdResponse.getFraud());
assertEquals(Boolean.TRUE, getLoansLoanIdResponse.getFraud());
statusCode = getLoansLoanIdResponse.getStatus().getCode();
log.info("Loan with Id {} is with Status {}", getLoansLoanIdResponse.getId(), statusCode);
undoDisbursement(loanId);
getLoansLoanIdResponse = loanTransactionHelper.getLoan(requestSpec, responseSpec, loanId);
assertNotNull(getLoansLoanIdResponse);
assertNotNull(getLoansLoanIdResponse.getFraud());
assertEquals(Boolean.TRUE, getLoansLoanIdResponse.getFraud());
statusCode = getLoansLoanIdResponse.getStatus().getCode();
log.info("Loan with Id {} is with Status {}", getLoansLoanIdResponse.getId(), statusCode);
});
} }
private Integer createAccounts(final Integer daysToSubtract, final Integer numberOfRepayments) {
// Client and Loan account creation
final Integer clientId = ClientHelper.createClient(this.requestSpec, this.responseSpec, "01 January 2012");
final GetLoanProductsProductIdResponse getLoanProductsProductResponse = createLoanProduct(loanTransactionHelper, null);
// Older date to have more than one overdue installment
final LocalDate transactionDate = this.todaysDate.minusDays(daysToSubtract + (30 * (numberOfRepayments - 1)));
String operationDate = Utils.dateFormatter.format(transactionDate);
return createLoanAccount(loanTransactionHelper, clientId.toString(), getLoanProductsProductResponse.getId().toString(),
operationDate, amountVal, numberOfRepayments.toString());
}
private GetLoanProductsProductIdResponse createLoanProduct(final LoanTransactionHelper loanTransactionHelper,
final Integer delinquencyBucketId) {
final HashMap<String, Object> loanProductMap = new LoanProductTestBuilder().build(null, delinquencyBucketId);
final Integer loanProductId = loanTransactionHelper.getLoanProductId(Utils.convertToJson(loanProductMap));
return loanTransactionHelper.getLoanProduct(loanProductId);
}
private Integer createLoanAccount(final LoanTransactionHelper loanTransactionHelper, final String clientId, final String loanProductId,
final String operationDate, final String principalAmount, final String numberOfRepayments) {
final String loanApplicationJSON = new LoanApplicationTestBuilder().withPrincipal(principalAmount)
.withLoanTermFrequency(numberOfRepayments).withLoanTermFrequencyAsMonths().withNumberOfRepayments(numberOfRepayments)
.withRepaymentEveryAfter("1").withRepaymentFrequencyTypeAsMonths() //
.withInterestRatePerPeriod("0") //
.withExpectedDisbursementDate(operationDate) //
.withInterestTypeAsDecliningBalance() //
.withSubmittedOnDate(operationDate) //
.build(clientId, loanProductId, null);
return loanTransactionHelper.getLoanId(loanApplicationJSON);
}
} }