Skip to content

Commit

Permalink
Merge remote-tracking branch 'origin/UXPROD-5001' into UXPROD-5001
Browse files Browse the repository at this point in the history
# Conflicts:
#	src/main/java/org/folio/dcb/listener/kafka/CirculationEventListener.java
#	src/main/java/org/folio/dcb/listener/kafka/EventData.java
#	src/main/java/org/folio/dcb/service/impl/CirculationServiceImpl.java
  • Loading branch information
AntonAntonich committed Dec 10, 2024
2 parents e5ce55d + 2c13aab commit 33a63af
Show file tree
Hide file tree
Showing 18 changed files with 179 additions and 66 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
import lombok.AllArgsConstructor;
import lombok.extern.log4j.Log4j2;
import org.folio.dcb.domain.dto.DcbTransaction;
import org.folio.dcb.domain.dto.DcbTransactionUpdate;
import org.folio.dcb.domain.dto.DcbUpdateTransaction;
import org.folio.dcb.domain.dto.TransactionStatus;
import org.folio.dcb.domain.dto.TransactionStatusResponseCollection;
import org.folio.dcb.rest.resource.TransactionsApi;
Expand Down Expand Up @@ -76,8 +76,8 @@ public ResponseEntity<TransactionStatusResponseCollection> getTransactionStatusL
}

@Override
public ResponseEntity<Void> updateTransactionDetails(String dcbTransactionId, DcbTransactionUpdate dcbTransactionUpdate) {
transactionsService.updateTransactionDetails(dcbTransactionId, dcbTransactionUpdate);
public ResponseEntity<Void> updateTransactionDetails(String dcbTransactionId, DcbUpdateTransaction dcbUpdateTransaction) {
transactionsService.updateTransactionDetails(dcbTransactionId, dcbUpdateTransaction);
return ResponseEntity.status(HttpStatus.NO_CONTENT)
.build();
}
Expand Down
10 changes: 5 additions & 5 deletions src/main/java/org/folio/dcb/domain/mapper/TransactionMapper.java
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
import org.folio.dcb.domain.dto.DcbItem;
import org.folio.dcb.domain.dto.DcbPatron;
import org.folio.dcb.domain.dto.DcbPickup;
import org.folio.dcb.domain.dto.DcbTransactionUpdateItem;
import org.folio.dcb.domain.dto.DcbUpdateItem;
import org.folio.dcb.domain.dto.TransactionStatusResponseList;
import org.folio.dcb.domain.entity.TransactionAuditEntity;
import org.folio.dcb.domain.entity.TransactionEntity;
Expand Down Expand Up @@ -92,12 +92,12 @@ public DcbPickup mapTransactionEntityToDcbPickup(TransactionEntity transactionEn
.build();
}

public DcbItem convertTransactionUpdateItemToDcbItem(DcbTransactionUpdateItem updatedItem, TransactionEntity entity) {
public DcbItem convertTransactionUpdateItemToDcbItem(DcbUpdateItem dcbUpdateItem, TransactionEntity entity) {
return DcbItem
.builder()
.lendingLibraryCode(updatedItem.getLendingLibraryCode())
.barcode(updatedItem.getBarcode())
.materialType(updatedItem.getMaterialType())
.lendingLibraryCode(dcbUpdateItem.getLendingLibraryCode())
.barcode(dcbUpdateItem.getBarcode())
.materialType(dcbUpdateItem.getMaterialType())
.title(entity.getItemTitle())
.build();
}
Expand Down
3 changes: 1 addition & 2 deletions src/main/java/org/folio/dcb/service/CirculationService.java
Original file line number Diff line number Diff line change
Expand Up @@ -20,8 +20,7 @@ public interface CirculationService {
/**
* Cancels a transaction request based on the provided transaction details.
* <p>
* If {@code isItemUnavailableCancellation} is {@code true}, the cancellation reason
* will be updated to indicate item unavailability, and the notification for this
* If {@code isItemUnavailableCancellation} is {@code true}, the notification for this
* cancellation will be suppressed by setting the {@code suppressNotification} flag
* to {@code true}.
* </p>
Expand Down
4 changes: 2 additions & 2 deletions src/main/java/org/folio/dcb/service/TransactionsService.java
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
package org.folio.dcb.service;

import org.folio.dcb.domain.dto.DcbTransaction;
import org.folio.dcb.domain.dto.DcbTransactionUpdate;
import org.folio.dcb.domain.dto.DcbUpdateTransaction;
import org.folio.dcb.domain.dto.TransactionStatus;
import org.folio.dcb.domain.dto.TransactionStatusResponse;
import org.folio.dcb.domain.dto.TransactionStatusResponseCollection;
Expand All @@ -18,6 +18,6 @@ public interface TransactionsService {
TransactionStatusResponse updateTransactionStatus(String dcbTransactionId, TransactionStatus transactionStatus);
TransactionStatusResponse getTransactionStatusById(String dcbTransactionId);
TransactionStatusResponseCollection getTransactionStatusList(OffsetDateTime fromDate, OffsetDateTime toDate, Integer pageNumber, Integer pageSize);
void updateTransactionDetails(String dcbTransactionId, DcbTransactionUpdate dcbTransactionUpdate);
void updateTransactionDetails(String dcbTransactionId, DcbUpdateTransaction dcbUpdateTransaction);

}
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@
import org.folio.dcb.domain.dto.DcbItem;
import org.folio.dcb.domain.dto.DcbPatron;
import org.folio.dcb.domain.dto.DcbTransaction;
import org.folio.dcb.domain.dto.DcbTransactionUpdateItem;
import org.folio.dcb.domain.dto.DcbUpdateItem;
import org.folio.dcb.domain.dto.TransactionStatus;
import org.folio.dcb.domain.dto.TransactionStatusResponse;
import org.folio.dcb.domain.entity.TransactionEntity;
Expand Down Expand Up @@ -138,9 +138,9 @@ public void updateTransactionEntity(TransactionEntity transactionEntity, Transac
transactionRepository.save(transactionEntity);
}

public void updateTransactionDetails(TransactionEntity transactionEntity, DcbTransactionUpdateItem updatedItem) {
public void updateTransactionDetails(TransactionEntity transactionEntity, DcbUpdateItem dcbUpdateItem) {
DcbPatron dcbPatron = transactionMapper.mapTransactionEntityToDcbPatron(transactionEntity);
DcbItem dcbItem = transactionMapper.convertTransactionUpdateItemToDcbItem(updatedItem, transactionEntity);
DcbItem dcbItem = transactionMapper.convertTransactionUpdateItemToDcbItem(dcbUpdateItem, transactionEntity);
checkItemExistsInInventoryAndThrow(dcbItem.getBarcode());
CirculationItem item = circulationItemService.checkIfItemExistsAndCreate(dcbItem, transactionEntity.getServicePointId());
dcbItem.setId(item.getId());
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
import lombok.RequiredArgsConstructor;
import lombok.extern.log4j.Log4j2;
import org.folio.dcb.domain.dto.DcbTransaction;
import org.folio.dcb.domain.dto.DcbTransactionUpdate;
import org.folio.dcb.domain.dto.DcbUpdateTransaction;
import org.folio.dcb.domain.dto.TransactionStatus;
import org.folio.dcb.domain.dto.TransactionStatusResponse;
import org.folio.dcb.domain.dto.TransactionStatusResponseCollection;
Expand Down Expand Up @@ -112,7 +112,7 @@ public TransactionStatusResponseCollection getTransactionStatusList(OffsetDateTi
}

@Override
public void updateTransactionDetails(String dcbTransactionId, DcbTransactionUpdate dcbTransactionUpdate) {
public void updateTransactionDetails(String dcbTransactionId, DcbUpdateTransaction dcbUpdateTransaction) {
var transactionEntity = getTransactionEntityOrThrow(dcbTransactionId);
if (!TransactionStatus.StatusEnum.CREATED.equals(transactionEntity.getStatus())) {
throw new StatusException(String.format(
Expand All @@ -121,7 +121,7 @@ public void updateTransactionDetails(String dcbTransactionId, DcbTransactionUpda
if (DcbTransaction.RoleEnum.LENDER.equals(transactionEntity.getRole())) {
throw new IllegalArgumentException("Item details cannot be updated for lender role");
}
baseLibraryService.updateTransactionDetails(transactionEntity, dcbTransactionUpdate.getItem());
baseLibraryService.updateTransactionDetails(transactionEntity, dcbUpdateTransaction.getItem());
}

private TransactionStatusResponse generateTransactionStatusResponseFromTransactionEntity(TransactionEntity transactionEntity) {
Expand Down
3 changes: 0 additions & 3 deletions src/main/java/org/folio/dcb/utils/TransactionHelper.java
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,6 @@ public class TransactionHelper {
public static final String LASTNAME = "lastName";
public static final String DCB_INSTANCE_TITLE = "DCB_INSTANCE";
public static final String DCB_REQUESTER_LASTNAME = "DcbSystem";
public static final String CANCELLATION_ADDITIONAL_INFORMATION = "cancellationAdditionalInformation";

private TransactionHelper(){}

Expand Down Expand Up @@ -67,8 +66,6 @@ public static EventData parseRequestEvent(String eventPayload){
default -> log.info("parseRequestEvent:: Request status {} is not supported", requestStatus);
}
eventData.setDcb(checkDcbRequest(kafkaEvent));
eventData.setCancellationAdditionalInformation(kafkaEvent.getNewNode().has(CANCELLATION_ADDITIONAL_INFORMATION) ?
kafkaEvent.getNewNode().get(CANCELLATION_ADDITIONAL_INFORMATION).asText() : null);
return eventData;
}
return null;
Expand Down
6 changes: 3 additions & 3 deletions src/main/resources/swagger.api/dcb_transaction.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@ paths:
parameters:
- $ref: '#/components/parameters/dcbTransactionId'
requestBody:
$ref: "#/components/requestBodies/DCBTransactionUpdate"
$ref: "#/components/requestBodies/DcbUpdateTransaction"
responses:
'204':
description: 'Transaction updated successfully'
Expand Down Expand Up @@ -126,13 +126,13 @@ components:
application/json:
schema:
$ref: "schemas/dcbTransaction.yaml#/DcbTransaction"
DCBTransactionUpdate:
DcbUpdateTransaction:
description: DCB transaction update object
required: true
content:
application/json:
schema:
$ref: "schemas/DcbTransactionUpdate.yaml#/DcbTransactionUpdate"
$ref: "schemas/dcbUpdateTransaction.yaml#/DcbUpdateTransaction"
responses:
TransactionStatus:
description: Transaction Status object
Expand Down
20 changes: 0 additions & 20 deletions src/main/resources/swagger.api/schemas/DcbTransactionUpdate.yaml

This file was deleted.

18 changes: 18 additions & 0 deletions src/main/resources/swagger.api/schemas/dcbUpdateItem.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
DcbUpdateItem:
description: Item metadata required for updating the existing transaction
type: object
properties:
barcode:
description: The barcode of the item as specified in the lending library
type: string
materialType:
description: The “hub-normalized” form of the item item type, used in the circulation rules for determining the correct loan policy.
type: string
lendingLibraryCode:
description: The code which identifies the lending library
type: string
additionalProperties: false
required:
- barcode
- materialType
- lendingLibraryCode
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
DcbUpdateTransaction:
type: object
properties:
item:
$ref: 'dcbUpdateItem.yaml#/DcbUpdateItem'

Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package org.folio.dcb.controller;

import com.jayway.jsonpath.JsonPath;
import org.folio.dcb.domain.dto.DcbItem;
import org.folio.dcb.domain.dto.TransactionStatus;
import org.folio.dcb.domain.entity.TransactionAuditEntity;
Expand All @@ -10,6 +11,7 @@
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.MediaType;
import org.springframework.test.web.servlet.MvcResult;

import java.time.OffsetDateTime;
import java.time.ZoneOffset;
Expand All @@ -19,6 +21,7 @@
import static org.folio.dcb.domain.dto.DcbTransaction.RoleEnum.BORROWING_PICKUP;
import static org.folio.dcb.domain.dto.DcbTransaction.RoleEnum.LENDER;
import static org.folio.dcb.domain.dto.DcbTransaction.RoleEnum.PICKUP;
import static org.folio.dcb.utils.EntityUtils.DCB_NEW_BARCODE;
import static org.folio.dcb.utils.EntityUtils.DCB_TRANSACTION_ID;
import static org.folio.dcb.utils.EntityUtils.DCB_TYPE_USER_ID;
import static org.folio.dcb.utils.EntityUtils.EXISTED_INVENTORY_ITEM_BARCODE;
Expand All @@ -28,13 +31,17 @@
import static org.folio.dcb.utils.EntityUtils.PATRON_TYPE_USER_ID;
import static org.folio.dcb.utils.EntityUtils.createDcbItem;
import static org.folio.dcb.utils.EntityUtils.createDcbPatronWithExactPatronId;
import static org.folio.dcb.utils.EntityUtils.createDcbTransactionUpdate;
import static org.folio.dcb.utils.EntityUtils.createDefaultDcbPatron;
import static org.folio.dcb.utils.EntityUtils.createDcbTransactionByRole;
import static org.folio.dcb.utils.EntityUtils.createTransactionEntity;
import static org.folio.dcb.utils.EntityUtils.createTransactionStatus;
import static org.hamcrest.Matchers.contains;
import static org.hamcrest.Matchers.containsInRelativeOrder;
import static org.hamcrest.Matchers.is;
import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.jupiter.api.Assertions.assertNotEquals;
import static org.junit.jupiter.api.Assertions.assertNotNull;
import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.get;
import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.post;
import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.put;
Expand Down Expand Up @@ -87,9 +94,9 @@ void createLendingCirculationRequestTest() throws Exception {
() -> {
TransactionAuditEntity auditExisting = transactionAuditRepository.findLatestTransactionAuditEntityByDcbTransactionId(DCB_TRANSACTION_ID)
.orElse(null);
Assertions.assertNotNull(auditExisting);
Assertions.assertNotEquals(TRANSACTION_AUDIT_DUPLICATE_ERROR_ACTION, auditExisting.getAction());
Assertions.assertNotEquals(DUPLICATE_ERROR_TRANSACTION_ID, auditExisting.getTransactionId()); }
assertNotNull(auditExisting);
assertNotEquals(TRANSACTION_AUDIT_DUPLICATE_ERROR_ACTION, auditExisting.getAction());
assertNotEquals(DUPLICATE_ERROR_TRANSACTION_ID, auditExisting.getTransactionId()); }
);
}

Expand Down Expand Up @@ -162,9 +169,9 @@ void createBorrowingPickupCirculationRequestTest() throws Exception {
() -> {
TransactionAuditEntity auditExisting = transactionAuditRepository.findLatestTransactionAuditEntityByDcbTransactionId(DCB_TRANSACTION_ID)
.orElse(null);
Assertions.assertNotNull(auditExisting);
Assertions.assertNotEquals(TRANSACTION_AUDIT_DUPLICATE_ERROR_ACTION, auditExisting.getAction());
Assertions.assertNotEquals(DUPLICATE_ERROR_TRANSACTION_ID, auditExisting.getTransactionId()); }
assertNotNull(auditExisting);
assertNotEquals(TRANSACTION_AUDIT_DUPLICATE_ERROR_ACTION, auditExisting.getAction());
assertNotEquals(DUPLICATE_ERROR_TRANSACTION_ID, auditExisting.getTransactionId()); }
);
}

Expand All @@ -190,8 +197,8 @@ void createLendingCirculationRequestWithInvalidItemId() throws Exception {
() -> {
TransactionAuditEntity auditExisting = transactionAuditRepository.findLatestTransactionAuditEntityByDcbTransactionId(trnId)
.orElse(null);
Assertions.assertNotNull(auditExisting);
Assertions.assertEquals(TRANSACTION_AUDIT_ERROR_ACTION, auditExisting.getAction()); }
assertNotNull(auditExisting);
assertEquals(TRANSACTION_AUDIT_ERROR_ACTION, auditExisting.getAction()); }
);
}

Expand All @@ -216,8 +223,8 @@ void createBorrowingPickupCirculationRequestWithInvalidDefaultNotExistedPatronId
() -> {
TransactionAuditEntity auditExisting = transactionAuditRepository.findLatestTransactionAuditEntityByDcbTransactionId(trnId)
.orElse(null);
Assertions.assertNotNull(auditExisting);
Assertions.assertEquals(TRANSACTION_AUDIT_ERROR_ACTION, auditExisting.getAction()); }
assertNotNull(auditExisting);
assertEquals(TRANSACTION_AUDIT_ERROR_ACTION, auditExisting.getAction()); }
);
}

Expand Down Expand Up @@ -455,9 +462,9 @@ void createTransactionForPickupLibrary() throws Exception {
() -> {
TransactionAuditEntity auditExisting = transactionAuditRepository.findLatestTransactionAuditEntityByDcbTransactionId(DCB_TRANSACTION_ID)
.orElse(null);
Assertions.assertNotNull(auditExisting);
Assertions.assertNotEquals(TRANSACTION_AUDIT_DUPLICATE_ERROR_ACTION, auditExisting.getAction());
Assertions.assertNotEquals(DUPLICATE_ERROR_TRANSACTION_ID, auditExisting.getTransactionId()); }
assertNotNull(auditExisting);
assertNotEquals(TRANSACTION_AUDIT_DUPLICATE_ERROR_ACTION, auditExisting.getAction());
assertNotEquals(DUPLICATE_ERROR_TRANSACTION_ID, auditExisting.getTransactionId()); }
);
}

Expand Down Expand Up @@ -513,9 +520,9 @@ void createBorrowerCirculationRequestTest() throws Exception {
() -> {
TransactionAuditEntity auditExisting = transactionAuditRepository.findLatestTransactionAuditEntityByDcbTransactionId(DCB_TRANSACTION_ID)
.orElse(null);
Assertions.assertNotNull(auditExisting);
Assertions.assertNotEquals(TRANSACTION_AUDIT_DUPLICATE_ERROR_ACTION, auditExisting.getAction());
Assertions.assertNotEquals(DUPLICATE_ERROR_TRANSACTION_ID, auditExisting.getTransactionId()); }
assertNotNull(auditExisting);
assertNotEquals(TRANSACTION_AUDIT_DUPLICATE_ERROR_ACTION, auditExisting.getAction());
assertNotEquals(DUPLICATE_ERROR_TRANSACTION_ID, auditExisting.getTransactionId()); }
);
}

Expand All @@ -537,7 +544,10 @@ void createBorrowerCirculationRequestWithoutExistingItemTest() throws Exception
.accept(MediaType.APPLICATION_JSON))
.andExpect(status().isCreated())
.andExpect(jsonPath("$.status").value("CREATED"))
.andExpect(jsonPath("$.item").value(dcbItem))
.andExpect(jsonPath("$.item.barcode").value(dcbItem.getBarcode()))
.andExpect(jsonPath("$.item.materialType").value(dcbItem.getMaterialType()))
.andExpect(jsonPath("$.item.lendingLibraryCode").value(dcbItem.getLendingLibraryCode()))
.andExpect(jsonPath("$.item.title").value(dcbItem.getTitle()))
.andExpect(jsonPath("$.patron").value(createDcbPatronWithExactPatronId(EXISTED_PATRON_ID)));

//Trying to create another transaction with same transaction id
Expand Down Expand Up @@ -983,9 +993,58 @@ void getTransactionStatusUpdateListTest() throws Exception {
.andExpect(jsonPath("$.maximumPageNumber", is(2)))
.andExpect(jsonPath("$.transactions[*].status",
containsInRelativeOrder("ITEM_CHECKED_OUT", "ITEM_CHECKED_IN")));
}

@Test
void createAndUpdateBorrowerTransactionTest() throws Exception {
removeExistedTransactionFromDbIfSoExists();
removeExistingTransactionsByItemId(ITEM_ID);

MvcResult result = this.mockMvc.perform(
post("/transactions/" + DCB_TRANSACTION_ID)
.content(asJsonString(createDcbTransactionByRole(BORROWER)))
.headers(defaultHeaders())
.contentType(MediaType.APPLICATION_JSON)
.accept(MediaType.APPLICATION_JSON))
.andExpect(status().isCreated())
.andExpect(jsonPath("$.status").value("CREATED"))
.andExpect(jsonPath("$.item").value(createDcbItem()))
.andExpect(jsonPath("$.patron").value(createDcbPatronWithExactPatronId(EXISTED_PATRON_ID)))
.andReturn(); // Capture the response for assertion

String responseContent = result.getResponse().getContentAsString();
String itemId = JsonPath.parse(responseContent).read("$.item.id", String.class);
String itemBarcode = JsonPath.parse(responseContent).read("$.item.barcode", String.class);
String lendingLibraryCode = JsonPath.parse(responseContent).read("$.item.lendingLibraryCode", String.class);
String materialType = JsonPath.parse(responseContent).read("$.item.materialType", String.class);

//Trying to update the transaction with same transaction id
this.mockMvc.perform(
put("/transactions/" + DCB_TRANSACTION_ID)
.content(asJsonString(createDcbTransactionUpdate()))
.headers(defaultHeaders())
.contentType(MediaType.APPLICATION_JSON)
.accept(MediaType.APPLICATION_JSON))
.andExpectAll(status().isNoContent());

// check whether item related data is updated
systemUserScopedExecutionService.executeAsyncSystemUserScoped(
TENANT,
() -> {
var transactionEntity = transactionRepository.findById(DCB_TRANSACTION_ID)
.orElse(null);
assertNotNull(transactionEntity);
assertNotEquals(itemId, transactionEntity.getItemId());
assertNotEquals(itemBarcode, transactionEntity.getItemBarcode());
assertEquals(DCB_NEW_BARCODE, transactionEntity.getItemBarcode());
assertNotEquals(lendingLibraryCode, transactionEntity.getLendingLibraryCode());
assertEquals("LEN", transactionEntity.getLendingLibraryCode());
assertNotEquals(materialType, transactionEntity.getMaterialType());
assertEquals("DVD", transactionEntity.getMaterialType());
});
}


private void removeExistedTransactionFromDbIfSoExists() {
systemUserScopedExecutionService.executeAsyncSystemUserScoped(TENANT, () -> {
if (transactionRepository.existsById(DCB_TRANSACTION_ID)){
Expand Down
Loading

0 comments on commit 33a63af

Please sign in to comment.