Skip to content

Commit

Permalink
[MODORDERS-1220]. Update validation to prevent adding piece to an pen…
Browse files Browse the repository at this point in the history
…ding order with synchronized status (#1068)

* MODORDERS-1183. Introduce new error code for missed affiliations

* MODORDERS-1220. Update validation to prevent adding piece to an pending order with synchronized status

* MODORDERS-1220. Revert unnecessary change

* MODORDERS-1220. Fix unit tests with mocks server
  • Loading branch information
SerhiiNosko authored Dec 13, 2024
1 parent 647fcff commit 777b6da
Show file tree
Hide file tree
Showing 9 changed files with 140 additions and 54 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -108,6 +108,7 @@ public enum ErrorCodes {
POSTGRE_SQL_ERROR("pgException", "PostgreSQL exception"),
PIECE_FORMAT_IS_NOT_VALID_ERROR("pieceFormatIsNotValid", "Piece format %s is not compatible with purchase line %s"),
PIECE_DISPLAY_ON_HOLDINGS_IS_NOT_CONSISTENT("pieceDisplayOnHoldingsIsNotConsistent", "Display On Holdings could not be set to false when Display To Public is true"),
PIECE_RELATED_ORDER_DATA_IS_NOT_VALID("pieceRelatedOrderDataIsNotValid", "Adding piece for pending order with synchronized workflow is not allowed"),
CREATE_PIECE_FOR_PENDING_ORDER_ERROR("createPiecePendingOrderError", "Creating piece for pending order is not possible. Please open order."),
CREATE_ITEM_FOR_PIECE_IS_NOT_ALLOWED_ERROR("createItemForPieceIsNotAllowedError", "Create item for piece format %s is not allowed. Please check inventory option in the purchase order line %s"),
NOT_FOUND("notFound", "Not Found"),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@
import org.folio.rest.RestConstants;
import org.folio.rest.core.exceptions.HttpException;
import org.folio.rest.jaxrs.model.CompositePoLine;
import org.folio.rest.jaxrs.model.CompositePurchaseOrder;
import org.folio.rest.jaxrs.model.Eresource;
import org.folio.rest.jaxrs.model.Error;
import org.folio.rest.jaxrs.model.Errors;
Expand All @@ -27,16 +28,17 @@
public class DefaultPieceFlowsValidator {
private static final Logger logger = LogManager.getLogger(DefaultPieceFlowsValidator.class);

public void isPieceRequestValid(Piece pieceToCreate, CompositePoLine originPoLine, boolean isCreateItem) {
List<Error> combinedErrors = new ArrayList<>();
public void isPieceRequestValid(Piece pieceToCreate, CompositePurchaseOrder originalOrder, CompositePoLine originPoLine, boolean isCreateItem) {
List<Error> isItemCreateValidError = validateItemCreateFlag(pieceToCreate, originPoLine, isCreateItem);
combinedErrors.addAll(isItemCreateValidError);
List<Error> combinedErrors = new ArrayList<>(isItemCreateValidError);
List<Error> pieceLocationErrors = Optional.ofNullable(PieceValidatorUtil.validatePieceLocation(pieceToCreate, originPoLine)).orElse(new ArrayList<>());
combinedErrors.addAll(pieceLocationErrors);
List<Error> pieceFormatErrors = Optional.ofNullable(PieceValidatorUtil.validatePieceFormat(pieceToCreate, originPoLine)).orElse(new ArrayList<>());
combinedErrors.addAll(pieceFormatErrors);
List<Error> displayOnHoldingsErrors = validateDisplayOnHoldingsConsistency(pieceToCreate);
combinedErrors.addAll(displayOnHoldingsErrors);
List<Error> relatedOrderErrors = PieceValidatorUtil.validatePieceRelatedOrder(originalOrder, originPoLine);
combinedErrors.addAll(relatedOrderErrors);
if (CollectionUtils.isNotEmpty(combinedErrors)) {
Errors errors = new Errors().withErrors(combinedErrors).withTotalRecords(combinedErrors.size());
logger.error("Validation error : " + JsonObject.mapFrom(errors).encodePrettily());
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ public Future<Piece> createPiece(Piece pieceToCreate, boolean createItem, Reques
PieceCreationHolder holder = new PieceCreationHolder().withPieceToCreate(pieceToCreate).withCreateItem(createItem);
return basePieceFlowHolderBuilder.updateHolderWithOrderInformation(holder, requestContext)
.compose(aHolder -> basePieceFlowHolderBuilder.updateHolderWithTitleInformation(holder, requestContext))
.map(v -> {defaultPieceFlowsValidator.isPieceRequestValid(pieceToCreate, holder.getOriginPoLine(), createItem); return null;})
.map(v -> {defaultPieceFlowsValidator.isPieceRequestValid(pieceToCreate, holder.getOriginPurchaseOrder(), holder.getOriginPoLine(), createItem); return null;})
.compose(order -> protectionService.isOperationRestricted(holder.getTitle().getAcqUnitIds(), ProtectedOperationType.CREATE, requestContext))
.compose(v -> pieceCreateFlowInventoryManager.processInventory(holder.getPurchaseOrderToSave(), holder.getPoLineToSave(), holder.getPieceToCreate(), holder.isCreateItem(), requestContext))
.compose(compPoLine -> updatePoLine(holder, requestContext))
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -82,7 +82,7 @@ public Future<Void> updatePiece(Piece pieceToUpdate, boolean createItem, boolean
.map(holder::withPieceFromStorage)
.compose(aHolder -> basePieceFlowHolderBuilder.updateHolderWithOrderInformation(holder, requestContext))
.compose(aHolder -> basePieceFlowHolderBuilder.updateHolderWithTitleInformation(holder, requestContext))
.compose(v -> asFuture(() -> defaultPieceFlowsValidator.isPieceRequestValid(pieceToUpdate, holder.getOriginPoLine(), createItem)))
.compose(v -> asFuture(() -> defaultPieceFlowsValidator.isPieceRequestValid(pieceToUpdate, holder.getOriginPurchaseOrder(), holder.getOriginPoLine(), createItem)))
.compose(title -> protectionService.isOperationRestricted(holder.getTitle().getAcqUnitIds(), UPDATE, requestContext))
.compose(v -> pieceUpdateFlowInventoryManager.processInventory(holder, requestContext))
.compose(v -> updatePoLine(holder, requestContext))
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,8 @@

import org.folio.rest.core.exceptions.ErrorCodes;
import org.folio.rest.jaxrs.model.CompositePoLine;
import org.folio.rest.jaxrs.model.CompositePurchaseOrder;
import org.folio.rest.jaxrs.model.CompositePurchaseOrder.WorkflowStatus;
import org.folio.rest.jaxrs.model.Eresource;
import org.folio.rest.jaxrs.model.Error;
import org.folio.rest.jaxrs.model.Physical;
Expand All @@ -40,6 +42,17 @@ public static List<Error> validatePieceFormat(Piece piece, CompositePoLine compo
return Collections.emptyList();
}

public static List<Error> validatePieceRelatedOrder(CompositePurchaseOrder order, CompositePoLine poLine) {
if (order == null || poLine == null) {
return Collections.emptyList();
}
if (WorkflowStatus.PENDING == order.getWorkflowStatus() && Boolean.FALSE.equals(poLine.getCheckinItems())) {
return List.of(new Error().withCode(ErrorCodes.PIECE_RELATED_ORDER_DATA_IS_NOT_VALID.getCode())
.withMessage(ErrorCodes.PIECE_RELATED_ORDER_DATA_IS_NOT_VALID.getDescription()));
}
return Collections.emptyList();
}

public static boolean isLocationRequired(Piece.Format pieceFormat, CompositePoLine compPOL) {
if (ELECTRONIC.equals(pieceFormat)) {
return compPOL.getEresource() != null &&
Expand Down
11 changes: 11 additions & 0 deletions src/test/java/org/folio/rest/impl/PieceApiTest.java
Original file line number Diff line number Diff line change
Expand Up @@ -266,6 +266,11 @@ void testPostShouldSuccessfullyCreatePieceWithoutReceiptDate() {
void testPutPiecesByIdTest() throws Exception {
logger.info("=== Test update piece by id - valid Id 204 ===");

CompositePoLine poLineForOpenOrder = getMockAsJson(PO_LINES_COLLECTION).getJsonArray("poLines").getJsonObject(5).mapTo(CompositePoLine.class);
CompositePurchaseOrder compositePurchaseOrder = new CompositePurchaseOrder().withId(poLineForOpenOrder.getPurchaseOrderId()).withWorkflowStatus(CompositePurchaseOrder.WorkflowStatus.OPEN);
addMockEntry(PURCHASE_ORDER_STORAGE, compositePurchaseOrder);
addMockEntry(PO_LINES_STORAGE, poLineForOpenOrder);

String reqData = getMockData(PIECE_RECORDS_MOCK_DATA_PATH + "pieceRecord.json");
String pieceId = UUID.randomUUID().toString();
JsonObject pieceStorage = new JsonObject((reqData));
Expand All @@ -274,6 +279,7 @@ void testPutPiecesByIdTest() throws Exception {
JsonObject pieceRequest = new JsonObject((reqData));
pieceRequest.put(ID, pieceId);
pieceRequest.put("receivingStatus", "Received");
pieceRequest.put("poLineId", poLineForOpenOrder.getId());

addMockEntry(PIECES_STORAGE, pieceStorage);
verifyPut(String.format(PIECES_ID_PATH, pieceId), pieceRequest, "", 204);
Expand Down Expand Up @@ -339,6 +345,11 @@ void testPutPiecesByIdEcs(String purchaseOrderId, String pieceId, boolean mockIt
void testPutPiecesByIdConsistentReceiptStatusTest() throws Exception {
logger.info("=== Test update piece by id when receipt status is consistent - valid Id 204 ===");

CompositePoLine poLineForOpenOrder = getMockAsJson(PO_LINES_COLLECTION).getJsonArray("poLines").getJsonObject(5).mapTo(CompositePoLine.class);
CompositePurchaseOrder compositePurchaseOrder = new CompositePurchaseOrder().withId(poLineForOpenOrder.getPurchaseOrderId()).withWorkflowStatus(CompositePurchaseOrder.WorkflowStatus.OPEN);
addMockEntry(PURCHASE_ORDER_STORAGE, compositePurchaseOrder);
addMockEntry(PO_LINES_STORAGE, poLineForOpenOrder);

String reqData = getMockData(PIECE_RECORDS_MOCK_DATA_PATH + "pieceRecord-received-consistent-receipt-status-5b454292-6aaa-474f-9510-b59a564e0c8d2.json");

verifyPut(String.format(PIECES_ID_PATH, CONSISTENT_RECEIVED_STATUS_PIECE_UUID), reqData, "", 204);
Expand Down
Loading

0 comments on commit 777b6da

Please sign in to comment.