From 3811d8aa4e8e4bc95c160d73667c9dc81e50aa31 Mon Sep 17 00:00:00 2001 From: azizbekxm Date: Tue, 14 Nov 2023 18:43:43 +0500 Subject: [PATCH] [MODAUD-174] - Implemented status change history feature and cleaned code --- .../acquisition/impl/OrderEventsDaoImpl.java | 9 +- .../impl/OrderLineEventsDaoImpl.java | 8 +- .../acquisition/impl/PieceEventsDaoImpl.java | 15 ++- .../rest/impl/AuditDataAcquisitionImpl.java | 95 +++++++++---------- 4 files changed, 57 insertions(+), 70 deletions(-) diff --git a/mod-audit-server/src/main/java/org/folio/dao/acquisition/impl/OrderEventsDaoImpl.java b/mod-audit-server/src/main/java/org/folio/dao/acquisition/impl/OrderEventsDaoImpl.java index 202f8b9..f866e24 100644 --- a/mod-audit-server/src/main/java/org/folio/dao/acquisition/impl/OrderEventsDaoImpl.java +++ b/mod-audit-server/src/main/java/org/folio/dao/acquisition/impl/OrderEventsDaoImpl.java @@ -32,7 +32,7 @@ public class OrderEventsDaoImpl implements OrderEventsDao { public static final String TABLE_NAME = "acquisition_order_log"; public static final String GET_BY_ORDER_ID_SQL = "SELECT id, action, order_id, user_id, event_date, action_date, modified_content_snapshot," + - " FROM %s WHERE order_id = $1 %s LIMIT $2 OFFSET $3"; + " (SELECT count(*) AS total_records FROM %s WHERE order_id = $1) FROM %s WHERE order_id = $1 %s LIMIT $2 OFFSET $3"; public static final String INSERT_SQL = "INSERT INTO %s (id, action, order_id, user_id, event_date, action_date, modified_content_snapshot)" + " VALUES ($1, $2, $3, $4, $5, $6, $7)"; @@ -65,7 +65,7 @@ public Future getAuditEventsByOrderId(String orderId, try { LOGGER.info("getAuditEventsByOrderId:: Trying to Retrieve AuditEvent with order id : {}", orderId); String logTable = formatDBTableName(tenantId, TABLE_NAME); - String query = format(GET_BY_ORDER_ID_SQL, logTable, format(ORDER_BY_PATTERN, sortBy, sortOrder)); + String query = format(GET_BY_ORDER_ID_SQL, logTable, logTable, format(ORDER_BY_PATTERN, sortBy, sortOrder)); Tuple queryParams = Tuple.of(UUID.fromString(orderId), limit, offset); pgClientFactory.createInstance(tenantId).selectRead(query, queryParams, promise); } catch (Exception e) { @@ -98,13 +98,10 @@ private void makeSaveCall(Promise> promise, String query, OrderAudit private OrderAuditEventCollection mapRowToListOfOrderEvent(RowSet rowSet) { LOGGER.debug("mapRowToListOfOrderEvent:: Mapping row to List of Order Events"); OrderAuditEventCollection orderAuditEventCollection = new OrderAuditEventCollection(); - // set audit piece change record(s) by mapping rowSet one by one rowSet.iterator().forEachRemaining(row -> { orderAuditEventCollection.getOrderAuditEvents().add(mapRowToOrderEvent(row)); + orderAuditEventCollection.setTotalItems(row.getInteger(TOTAL_RECORDS_FIELD)); }); - // set total records - int totalRecords = orderAuditEventCollection.getOrderAuditEvents().size(); - orderAuditEventCollection.setTotalItems(totalRecords); LOGGER.info("mapRowToListOfOrderEvent:: Mapped row to List of Order Events"); return orderAuditEventCollection; } diff --git a/mod-audit-server/src/main/java/org/folio/dao/acquisition/impl/OrderLineEventsDaoImpl.java b/mod-audit-server/src/main/java/org/folio/dao/acquisition/impl/OrderLineEventsDaoImpl.java index 12da894..edae488 100644 --- a/mod-audit-server/src/main/java/org/folio/dao/acquisition/impl/OrderLineEventsDaoImpl.java +++ b/mod-audit-server/src/main/java/org/folio/dao/acquisition/impl/OrderLineEventsDaoImpl.java @@ -32,6 +32,7 @@ public class OrderLineEventsDaoImpl implements OrderLineEventsDao { public static final String TABLE_NAME = "acquisition_order_line_log"; public static final String GET_BY_ORDER_LINE_ID_SQL = "SELECT id, action, order_id, order_line_id, user_id, event_date, action_date, modified_content_snapshot," + + " (SELECT count(*) AS total_records FROM %s WHERE order_line_id = $1) " + " FROM %s WHERE order_line_id = $1 %s LIMIT $2 OFFSET $3"; private static final String INSERT_SQL = "INSERT INTO %s (id, action, order_id, order_line_id, user_id, event_date, action_date, modified_content_snapshot) " + @@ -66,7 +67,7 @@ public Future getAuditEventsByOrderLineId(String try { LOGGER.info("getAuditEventsByOrderLineId:: Trying to Retrieve AuditEvent with order line id : {}", orderLineId); String logTable = formatDBTableName(tenantId, TABLE_NAME); - String query = format(GET_BY_ORDER_LINE_ID_SQL, logTable, format(ORDER_BY_PATTERN, sortBy, sortOrder)); + String query = format(GET_BY_ORDER_LINE_ID_SQL, logTable, logTable, format(ORDER_BY_PATTERN, sortBy, sortOrder)); Tuple queryParams = Tuple.of(UUID.fromString(orderLineId), limit, offset); pgClientFactory.createInstance(tenantId).selectRead(query, queryParams, promise); } catch (Exception e) { @@ -100,13 +101,10 @@ private void makeSaveCall(Promise> promise, String query, OrderLineA private OrderLineAuditEventCollection mapRowToListOfOrderLineEvent(RowSet rowSet) { LOGGER.debug("mapRowToListOfOrderLineEvent:: Mapping row to List of Order Line Events"); OrderLineAuditEventCollection orderLineAuditEventCollection = new OrderLineAuditEventCollection(); - // set audit piece change record(s) by mapping rowSet one by one rowSet.iterator().forEachRemaining(row -> { orderLineAuditEventCollection.getOrderLineAuditEvents().add(mapRowToOrderLineEvent(row)); + orderLineAuditEventCollection.setTotalItems(row.getInteger(TOTAL_RECORDS_FIELD)); }); - // set total records - int totalRecords = orderLineAuditEventCollection.getOrderLineAuditEvents().size(); - orderLineAuditEventCollection.setTotalItems(totalRecords); LOGGER.info("mapRowToListOfOrderLineEvent:: Mapped row to List of Order Line Events"); return orderLineAuditEventCollection; } diff --git a/mod-audit-server/src/main/java/org/folio/dao/acquisition/impl/PieceEventsDaoImpl.java b/mod-audit-server/src/main/java/org/folio/dao/acquisition/impl/PieceEventsDaoImpl.java index 8f5107c..470a204 100644 --- a/mod-audit-server/src/main/java/org/folio/dao/acquisition/impl/PieceEventsDaoImpl.java +++ b/mod-audit-server/src/main/java/org/folio/dao/acquisition/impl/PieceEventsDaoImpl.java @@ -9,6 +9,7 @@ import static org.folio.util.AuditEventDBConstants.MODIFIED_CONTENT_FIELD; import static org.folio.util.AuditEventDBConstants.ORDER_BY_PATTERN; import static org.folio.util.AuditEventDBConstants.PIECE_ID_FIELD; +import static org.folio.util.AuditEventDBConstants.TOTAL_RECORDS_FIELD; import static org.folio.util.AuditEventDBConstants.USER_ID_FIELD; import java.time.LocalDateTime; @@ -36,13 +37,14 @@ public class PieceEventsDaoImpl implements PieceEventsDao { private static final Logger LOGGER = LogManager.getLogger(); private static final String TABLE_NAME = "acquisition_piece_log"; private static final String GET_BY_PIECE_ID_SQL = "SELECT id, action, piece_id, user_id, event_date, action_date, modified_content_snapshot" + - " FROM %s WHERE piece_id = $1 %s LIMIT $2 OFFSET $3"; + " (SELECT count(*) AS total_records FROM %s WHERE piece_id = $1) FROM %s WHERE piece_id = $1 %s LIMIT $2 OFFSET $3"; private static final String GET_STATUS_CHANGE_HISTORY_BY_PIECE_ID_SQL = """ WITH StatusChanges AS (SELECT id, action, piece_id, user_id, event_date, action_date, modified_content_snapshot, LAG(modified_content_snapshot ->> 'status') OVER (PARTITION BY piece_id ORDER BY action_date) AS previous_status FROM %s ) - SELECT id, action, piece_id, user_id, event_date, action_date, modified_content_snapshot FROM StatusChanges + SELECT id, action, piece_id, user_id, event_date, action_date, modified_content_snapshot, + (SELECT count(*) AS total_records FROM %s WHERE piece_id = $1) FROM StatusChanges WHERE piece_id = $1 and modified_content_snapshot ->> 'status' <> COALESCE(previous_status, '') %s LIMIT $2 OFFSET $3 """; @@ -76,7 +78,7 @@ public Future getAuditEventsByPieceId(String pieceId, Promise> promise = Promise.promise(); try { String logTable = formatDBTableName(tenantId, TABLE_NAME); - String query = format(GET_BY_PIECE_ID_SQL, logTable, format(ORDER_BY_PATTERN, sortBy, sortOrder)); + String query = format(GET_BY_PIECE_ID_SQL, logTable, logTable, format(ORDER_BY_PATTERN, sortBy, sortOrder)); Tuple queryParams = Tuple.of(UUID.fromString(pieceId), limit, offset); pgClientFactory.createInstance(tenantId).selectRead(query, queryParams, promise); } catch (Exception e) { @@ -96,7 +98,7 @@ public Future getAuditEventsWithUniqueStatusByPieceId try { LOGGER.info("getAuditEventsByOrderId:: Trying to Retrieve AuditEvent with piece id : {}", pieceId); String logTable = formatDBTableName(tenantId, TABLE_NAME); - String query = format(GET_STATUS_CHANGE_HISTORY_BY_PIECE_ID_SQL, logTable, format(ORDER_BY_PATTERN, sortBy, sortOrder)); + String query = format(GET_STATUS_CHANGE_HISTORY_BY_PIECE_ID_SQL, logTable, logTable, format(ORDER_BY_PATTERN, sortBy, sortOrder)); Tuple queryParams = Tuple.of(UUID.fromString(pieceId), limit, offset); pgClientFactory.createInstance(tenantId).selectRead(query, queryParams, promise); } catch (Exception e) { @@ -111,13 +113,10 @@ public Future getAuditEventsWithUniqueStatusByPieceId private PieceAuditEventCollection mapRowToListOfPieceEvent(RowSet rowSet) { LOGGER.debug("mapRowToListOfOrderEvent:: Mapping row to List of Piece Events"); PieceAuditEventCollection pieceAuditEventCollection = new PieceAuditEventCollection(); - // set audit piece change record(s) by mapping rowSet one by one rowSet.iterator().forEachRemaining(row -> { pieceAuditEventCollection.getPieceAuditEvents().add(mapRowToPieceEvent(row)); + pieceAuditEventCollection.setTotalItems(row.getInteger(TOTAL_RECORDS_FIELD)); }); - // set total records - int totalRecords = pieceAuditEventCollection.getPieceAuditEvents().size(); - pieceAuditEventCollection.setTotalItems(totalRecords); LOGGER.info("mapRowToListOfOrderEvent:: Mapped row to List of Piece Events"); return pieceAuditEventCollection; } diff --git a/mod-audit-server/src/main/java/org/folio/rest/impl/AuditDataAcquisitionImpl.java b/mod-audit-server/src/main/java/org/folio/rest/impl/AuditDataAcquisitionImpl.java index 5c3edaf..a895edb 100644 --- a/mod-audit-server/src/main/java/org/folio/rest/impl/AuditDataAcquisitionImpl.java +++ b/mod-audit-server/src/main/java/org/folio/rest/impl/AuditDataAcquisitionImpl.java @@ -48,19 +48,17 @@ public void getAuditDataAcquisitionOrderById(String orderId, String sortBy, Audi LOGGER.debug("getAuditDataAcquisitionOrderById:: Retrieving Audit Data Acquisition Order By Id : {}", orderId); String tenantId = TenantTool.tenantId(okapiHeaders); - vertxContext.runOnContext(c -> { - try { - LOGGER.warn("Trying to get audit events by order id: {}", orderId); - orderAuditEventsService.getAuditEventsByOrderId(orderId, sortBy, sortOrder.name(), limit, offset, tenantId) - .map(GetAuditDataAcquisitionOrderByIdResponse::respond200WithApplicationJson) - .map(Response.class::cast) - .otherwise(this::mapExceptionToResponse) - .onComplete(asyncResultHandler); - } catch (Exception e) { - LOGGER.warn("Failed to get order audit events by order id: {}", orderId, e); - asyncResultHandler.handle(Future.succeededFuture(mapExceptionToResponse(e))); - } - }); + try { + LOGGER.warn("Trying to get audit events by order id: {}", orderId); + orderAuditEventsService.getAuditEventsByOrderId(orderId, sortBy, sortOrder.name(), limit, offset, tenantId) + .map(GetAuditDataAcquisitionOrderByIdResponse::respond200WithApplicationJson) + .map(Response.class::cast) + .otherwise(this::mapExceptionToResponse) + .onComplete(asyncResultHandler); + } catch (Exception e) { + LOGGER.warn("Failed to get order audit events by order id: {}", orderId, e); + asyncResultHandler.handle(Future.succeededFuture(mapExceptionToResponse(e))); + } } @Override @@ -69,19 +67,18 @@ public void getAuditDataAcquisitionOrderLineById(String orderLineId, String sort LOGGER.debug("getAuditDataAcquisitionOrderLineById:: Retrieving Audit Data Acquisition Order Line By Id : {}", orderLineId); String tenantId = TenantTool.tenantId(okapiHeaders); - vertxContext.runOnContext(c -> { - try { - LOGGER.warn("Trying to get audit events by order line id: {}", orderLineId); - orderLineAuditEventsService.getAuditEventsByOrderLineId(orderLineId, sortBy, sortOrder.name(), limit, offset, tenantId) - .map(GetAuditDataAcquisitionOrderLineByIdResponse::respond200WithApplicationJson) - .map(Response.class::cast) - .otherwise(this::mapExceptionToResponse) - .onComplete(asyncResultHandler); - } catch (Exception e) { - LOGGER.warn("Failed to get order line audit events by order line id: {}", orderLineId, e); - asyncResultHandler.handle(Future.succeededFuture(mapExceptionToResponse(e))); - } - }); + try { + LOGGER.warn("Trying to get audit events by order line id: {}", orderLineId); + orderLineAuditEventsService.getAuditEventsByOrderLineId(orderLineId, sortBy, sortOrder.name(), limit, offset, tenantId) + .map(GetAuditDataAcquisitionOrderLineByIdResponse::respond200WithApplicationJson) + .map(Response.class::cast) + .otherwise(this::mapExceptionToResponse) + .onComplete(asyncResultHandler); + } catch (Exception e) { + LOGGER.warn("Failed to get order line audit events by order line id: {}", orderLineId, e); + asyncResultHandler.handle(Future.succeededFuture(mapExceptionToResponse(e))); + } + } @Override @@ -90,18 +87,16 @@ public void getAuditDataAcquisitionPieceById(String pieceId, String sortBy, Audi LOGGER.debug("getAuditDataAcquisitionOrderById:: Retrieving Audit Data Acquisition Piece By Id : {}", pieceId); String tenantId = TenantTool.tenantId(okapiHeaders); - vertxContext.runOnContext(c -> { - try { - pieceAuditEventsService.getAuditEventsByPieceId(pieceId, sortBy, sortOrder.name(), limit, offset, tenantId) - .map(GetAuditDataAcquisitionPieceByIdResponse::respond200WithApplicationJson) - .map(Response.class::cast) - .otherwise(this::mapExceptionToResponse) - .onComplete(asyncResultHandler); - } catch (Exception e) { - LOGGER.error("Failed to get piece audit events by piece id: {}", pieceId, e); - asyncResultHandler.handle(Future.succeededFuture(mapExceptionToResponse(e))); - } - }); + try { + pieceAuditEventsService.getAuditEventsByPieceId(pieceId, sortBy, sortOrder.name(), limit, offset, tenantId) + .map(GetAuditDataAcquisitionPieceByIdResponse::respond200WithApplicationJson) + .map(Response.class::cast) + .otherwise(this::mapExceptionToResponse) + .onComplete(asyncResultHandler); + } catch (Exception e) { + LOGGER.error("Failed to get piece audit events by piece id: {}", pieceId, e); + asyncResultHandler.handle(Future.succeededFuture(mapExceptionToResponse(e))); + } } @Override @@ -111,19 +106,17 @@ public void getAuditDataAcquisitionPieceStatusChangeHistoryById(String pieceId, LOGGER.debug("getAuditDataAcquisitionOrderById:: Retrieving Audit Data Acquisition Piece with unique status By Id : {}", pieceId); String tenantId = TenantTool.tenantId(okapiHeaders); - vertxContext.runOnContext(c -> { - try { - LOGGER.warn("Trying to get piece audit events with unique status by piece id: {}", pieceId); - pieceAuditEventsService.getAuditEventsWithUniqueStatusByPieceId(pieceId, sortBy, sortOrder.name(), limit, offset, tenantId) - .map(GetAuditDataAcquisitionPieceByIdResponse::respond200WithApplicationJson) - .map(Response.class::cast) - .otherwise(this::mapExceptionToResponse) - .onComplete(asyncResultHandler); - } catch (Exception e) { - LOGGER.warn("Failed to get piece audit events with unique status change by piece id: {}", pieceId, e); - asyncResultHandler.handle(Future.succeededFuture(mapExceptionToResponse(e))); - } - }); + try { + LOGGER.warn("Trying to get piece audit events with unique status by piece id: {}", pieceId); + pieceAuditEventsService.getAuditEventsWithUniqueStatusByPieceId(pieceId, sortBy, sortOrder.name(), limit, offset, tenantId) + .map(GetAuditDataAcquisitionPieceByIdResponse::respond200WithApplicationJson) + .map(Response.class::cast) + .otherwise(this::mapExceptionToResponse) + .onComplete(asyncResultHandler); + } catch (Exception e) { + LOGGER.warn("Failed to get piece audit events with unique status change by piece id: {}", pieceId, e); + asyncResultHandler.handle(Future.succeededFuture(mapExceptionToResponse(e))); + } } private Response mapExceptionToResponse(Throwable throwable) {