Added user action log and versioning for communication.
This commit is contained in:
@@ -5,14 +5,19 @@ import net.gepafin.tendermanagement.config.Translator;
|
||||
import net.gepafin.tendermanagement.constants.GepafinConstant;
|
||||
import net.gepafin.tendermanagement.entities.ApplicationAmendmentRequestEntity;
|
||||
import net.gepafin.tendermanagement.entities.CommunicationEntity;
|
||||
import net.gepafin.tendermanagement.enums.VersionActionTypeEnum;
|
||||
import net.gepafin.tendermanagement.model.request.CommunicationRequestBean;
|
||||
import net.gepafin.tendermanagement.model.request.VersionHistoryRequest;
|
||||
import net.gepafin.tendermanagement.model.response.ApplicationAmendmentResponse;
|
||||
import net.gepafin.tendermanagement.model.response.CommunicationResponseBean;
|
||||
import net.gepafin.tendermanagement.repositories.CommunicationRepository;
|
||||
import net.gepafin.tendermanagement.service.ApplicationAmendmentRequestService;
|
||||
import net.gepafin.tendermanagement.util.LoggingUtil;
|
||||
import net.gepafin.tendermanagement.util.Utils;
|
||||
import net.gepafin.tendermanagement.util.Validator;
|
||||
import net.gepafin.tendermanagement.web.rest.api.errors.CustomValidationException;
|
||||
import net.gepafin.tendermanagement.web.rest.api.errors.Status;
|
||||
import org.checkerframework.checker.units.qual.A;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
@@ -34,24 +39,41 @@ public class CommunicationDao {
|
||||
@Autowired
|
||||
private Validator validator;
|
||||
|
||||
@Autowired
|
||||
private LoggingUtil loggingUtil;
|
||||
|
||||
@Autowired
|
||||
private HttpServletRequest request;
|
||||
|
||||
public CommunicationResponseBean addCommentToAmendmentRequest(HttpServletRequest request, CommunicationRequestBean communicationReq, Long amendmentId) {
|
||||
|
||||
log.info("Adding communication request...");
|
||||
CommunicationEntity communicationEntity = convertToCommunicationCommentEntity(communicationReq, amendmentId);
|
||||
communicationEntity = communicationRepository.save(communicationEntity);
|
||||
|
||||
/** This code is responsible for adding a version history log for the "adding comment to amendment request" operation. **/
|
||||
loggingUtil.addVersionHistory(VersionHistoryRequest.builder().request(request).actionType(VersionActionTypeEnum.INSERT).oldData(null).newData(communicationEntity).build());
|
||||
|
||||
log.info("Added comment: {}", communicationEntity);
|
||||
return convertToCommunicationResponseBean(communicationEntity);
|
||||
}
|
||||
|
||||
public String deleteComment(Long amendmentId, Long commentId) {
|
||||
|
||||
CommunicationEntity data = communicationRepository.findById(commentId)
|
||||
CommunicationEntity data = communicationRepository.findByIdAndIsDeletedFalse(commentId)
|
||||
.orElseThrow(() -> new CustomValidationException(Status.NOT_FOUND, Translator.toLocale(GepafinConstant.COMMENT_NOT_FOUND)));
|
||||
//cloned for old commentData
|
||||
CommunicationEntity oldComment = Utils.getClonedEntityForData(data);
|
||||
|
||||
if (!data.getApplicationAmendmentRequest().getId().equals(amendmentId)) {
|
||||
throw new CustomValidationException(Status.BAD_REQUEST, Translator.toLocale(GepafinConstant.INVALID_AMENDMENT_FOR_COMMENT));
|
||||
}
|
||||
data.setIsDeleted(true);
|
||||
communicationRepository.save(data);
|
||||
data = communicationRepository.save(data);
|
||||
|
||||
/** This code is responsible for adding a version history log for the "soft deleting comment to amendment request" operation. **/
|
||||
loggingUtil.addVersionHistory(VersionHistoryRequest.builder().request(request).actionType(VersionActionTypeEnum.SOFT_DELETE).oldData(oldComment).newData(data).build());
|
||||
|
||||
return "Deleted Comment Successfully.";
|
||||
}
|
||||
|
||||
@@ -70,6 +92,9 @@ public class CommunicationDao {
|
||||
log.info("Updating communication comment...");
|
||||
CommunicationEntity existingComment = communicationRepository.findById(commentId)
|
||||
.orElseThrow(() -> new CustomValidationException(Status.NOT_FOUND, Translator.toLocale(GepafinConstant.COMMENT_NOT_FOUND)));
|
||||
//cloned for old data for communication
|
||||
CommunicationEntity oldCommentData = Utils.getClonedEntityForData(existingComment);
|
||||
|
||||
if (!existingComment.getApplicationAmendmentRequest().getId().equals(amendmentId)) {
|
||||
throw new CustomValidationException(Status.BAD_REQUEST, Translator.toLocale(GepafinConstant.COMMENT_NOT_ASSOCIATE_WITH_AMENDMENT_ID_ERROR_MSG));
|
||||
}
|
||||
@@ -78,6 +103,10 @@ public class CommunicationDao {
|
||||
existingComment.setCommentedDate(LocalDateTime.now());
|
||||
existingComment = communicationRepository.save(existingComment);
|
||||
log.info("Updated Comment: {}", existingComment);
|
||||
|
||||
/** This code is responsible for adding a version history log for the "updating comment to amendment request" operation. **/
|
||||
loggingUtil.addVersionHistory(VersionHistoryRequest.builder().request(request).actionType(VersionActionTypeEnum.UPDATE).oldData(oldCommentData).newData(existingComment).build());
|
||||
|
||||
return convertToCommunicationResponseBean(existingComment);
|
||||
}
|
||||
|
||||
@@ -92,6 +121,7 @@ public class CommunicationDao {
|
||||
response.setTitle(entity.getCommunicationTitle());
|
||||
response.setSenderUserId(entity.getSenderUserId());
|
||||
response.setReceiverUserId(entity.getReceiverUserId());
|
||||
response.setId(entity.getId());
|
||||
return response;
|
||||
}
|
||||
|
||||
|
||||
@@ -135,7 +135,13 @@ public enum UserActionContextEnum {
|
||||
GET_EVALUATION_CRITERIA("GET_EVALUATION_CRITERIA"),
|
||||
UPDATE_EVALUATION_CRITERIA("UPDATE_EVALUATION_CRITERIA"),
|
||||
DELETE_EVALUATION_CRITERIA("DELETE_EVALUATION_CRITERIA"),
|
||||
CREATE_EVALUATION_CRITERIA("CREATE_EVALUATION_CRITERIA");
|
||||
CREATE_EVALUATION_CRITERIA("CREATE_EVALUATION_CRITERIA"),
|
||||
|
||||
/** communication action context **/
|
||||
ADD_COMMENT_TO_AMENDMENT_REQUEST("ADD_COMMENT_TO_AMENDMENT_REQUEST"),
|
||||
UPDATE_COMMUNICATION_COMMENT("UPDATE_COMMUNICATION_COMMENT"),
|
||||
GET_AMENDMENT_COMMENT("GET_AMENDMENT_COMMENT"),
|
||||
DELETE_COMMENT_FROM_AMENDMENT("DELETE_COMMENT_FROM_AMENDMENT");
|
||||
|
||||
private final String value;
|
||||
|
||||
|
||||
@@ -10,6 +10,8 @@ public class CommunicationResponseBean {
|
||||
|
||||
private String comment;
|
||||
|
||||
private Long id;
|
||||
|
||||
private String title;
|
||||
|
||||
private LocalDateTime createdDate;
|
||||
@@ -21,7 +23,8 @@ public class CommunicationResponseBean {
|
||||
private Long receiverUserId;
|
||||
|
||||
private Long amendmentId;
|
||||
public CommunicationResponseBean(LocalDateTime commentedDate, String comment, String title, LocalDateTime createdDate, LocalDateTime updatedDate, Long amendmentId) {
|
||||
|
||||
public CommunicationResponseBean(LocalDateTime commentedDate, String comment, String title, LocalDateTime createdDate, LocalDateTime updatedDate, Long amendmentId, Long id) {
|
||||
|
||||
this.commentedDate = commentedDate;
|
||||
this.comment = comment;
|
||||
@@ -29,9 +32,10 @@ public class CommunicationResponseBean {
|
||||
this.createdDate = createdDate;
|
||||
this.updatedDate = updatedDate;
|
||||
this.amendmentId = amendmentId;
|
||||
this.id = id;
|
||||
}
|
||||
|
||||
public CommunicationResponseBean(LocalDateTime commentedDate, String comment, String title, LocalDateTime createdDate, LocalDateTime updatedDate, Long amendmentId,Long senderUserId,Long receiverUserId) {
|
||||
public CommunicationResponseBean(LocalDateTime commentedDate, String comment, String title, LocalDateTime createdDate, LocalDateTime updatedDate, Long amendmentId,Long senderUserId,Long receiverUserId, Long id) {
|
||||
|
||||
this.commentedDate = commentedDate;
|
||||
this.comment = comment;
|
||||
@@ -41,6 +45,7 @@ public class CommunicationResponseBean {
|
||||
this.amendmentId = amendmentId;
|
||||
this.senderUserId = senderUserId;
|
||||
this.receiverUserId = receiverUserId;
|
||||
this.id = id;
|
||||
}
|
||||
|
||||
public CommunicationResponseBean() {
|
||||
|
||||
@@ -7,16 +7,14 @@ import org.springframework.data.jpa.repository.Query;
|
||||
import org.springframework.data.repository.query.Param;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.Optional;
|
||||
|
||||
public interface CommunicationRepository extends JpaRepository<CommunicationEntity, Long> {
|
||||
|
||||
@Query("Select new net.gepafin.tendermanagement.model.response.CommunicationResponseBean(c.commentedDate, c.communicationComment, c.communicationTitle, c.createdDate, c.updatedDate, c.applicationAmendmentRequest.id) " +
|
||||
"from CommunicationEntity c Where c.applicationAmendmentRequest.id = :applicationAmendmentRequestId")
|
||||
List<CommunicationResponseBean> findCommentsByApplicationAmendmentRequestId(@Param("applicationAmendmentRequestId") Long amendmentRequestId);
|
||||
|
||||
@Query("SELECT new net.gepafin.tendermanagement.model.response.CommunicationResponseBean( " + "c.commentedDate, c.communicationComment, c.communicationTitle, c.createdDate, c" +
|
||||
".updatedDate, c.applicationAmendmentRequest.id,c.senderUserId, c.receiverUserId) " + "FROM CommunicationEntity c " + "WHERE c.applicationAmendmentRequest.id = :amendmentId AND c.isDeleted = false")
|
||||
".updatedDate, " + "c.applicationAmendmentRequest.id, c.senderUserId, c.receiverUserId, c.id " + ") " + "FROM CommunicationEntity c " + "WHERE c" +
|
||||
".applicationAmendmentRequest.id = :amendmentId AND c.isDeleted = false")
|
||||
List<CommunicationResponseBean> findCommentListDetailsByAmendmentId(@Param("amendmentId") Long amendmentId);
|
||||
|
||||
|
||||
Optional<CommunicationEntity> findByIdAndIsDeletedFalse(Long commentId);
|
||||
}
|
||||
|
||||
@@ -63,7 +63,7 @@ public class CommunicationServiceImpl implements CommunicationService {
|
||||
}
|
||||
|
||||
@Override
|
||||
@Transactional(readOnly = true)
|
||||
@Transactional(rollbackFor = Exception.class)
|
||||
public ApplicationAmendmentResponse getAmendmentComments(HttpServletRequest request,Long id) {
|
||||
ApplicationAmendmentRequestEntity applicationAmendmentRequestEntity = applicationAmendmentRequestDao.validateApplicationAmendmentRequest(id);
|
||||
if (Boolean.FALSE.equals(validator.checkIsBeneficiary())) {
|
||||
|
||||
@@ -19,6 +19,8 @@ import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Component;
|
||||
import org.springframework.web.context.annotation.RequestScope;
|
||||
|
||||
import java.net.URLDecoder;
|
||||
import java.nio.charset.StandardCharsets;
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
@@ -55,12 +57,26 @@ public class LoggingUtil {
|
||||
if (userActionRequest.getRequest() instanceof CachedBodyHttpServletRequest cachedRequest) {
|
||||
requestBody = cachedRequest.getCachedBodyAsString();
|
||||
}
|
||||
// Decode the raw URI to handle encoded placeholders like %7BcommentId%7D
|
||||
String rawUrl = userActionRequest.getRequest().getRequestURI();
|
||||
String decodedUrl = URLDecoder.decode(rawUrl, StandardCharsets.UTF_8);
|
||||
|
||||
// Append query parameters if they exist
|
||||
if (userActionRequest.getRequest().getQueryString() != null) {
|
||||
decodedUrl += "?" + userActionRequest.getRequest().getQueryString();
|
||||
}
|
||||
|
||||
// Use the decoded URL as-is (optional normalization step if needed)
|
||||
String normalizedUrl = normalizeUrl(decodedUrl);
|
||||
|
||||
// Set the normalized URL in the user action log
|
||||
userAction.setActionType(userActionRequest.getActionType().getValue());
|
||||
userAction.setUserId(userId);
|
||||
userAction.setActionContext(userActionRequest.getActionContext().getValue());
|
||||
userAction.setMethodType(userActionRequest.getRequest().getMethod());
|
||||
userAction.setHubId(userEntity.getHub().getId());
|
||||
userAction.setUrl(userActionRequest.getRequest().getRequestURI());
|
||||
// userAction.setUrl(userActionRequest.getRequest().getRequestURI());
|
||||
userAction.setUrl(normalizedUrl);
|
||||
userAction.setLoginAttemptId(loginAttemptId);
|
||||
userAction.setIpAddress(IpAddressUtils.getClientIp(userActionRequest.getRequest()));
|
||||
userAction.setRequestBody(requestBody);
|
||||
@@ -74,7 +90,18 @@ public class LoggingUtil {
|
||||
return userAction;
|
||||
}
|
||||
|
||||
// @Transactional
|
||||
private String normalizeUrl(String url) {
|
||||
|
||||
url = url.replaceAll("(?<!:)//+", "/");
|
||||
if (url.length() > 1 && url.endsWith("/")) {
|
||||
url = url.substring(0, url.length() - 1);
|
||||
}
|
||||
url = URLDecoder.decode(url, StandardCharsets.UTF_8);
|
||||
return url;
|
||||
}
|
||||
|
||||
|
||||
// @Transactional
|
||||
// public UserActionEntity updateUserAction(HttpServletResponse response, UserActionEntity userAction) {
|
||||
// try {
|
||||
// String requestBody = null;
|
||||
|
||||
@@ -3,11 +3,15 @@ package net.gepafin.tendermanagement.web.rest.api.impl;
|
||||
import jakarta.servlet.http.HttpServletRequest;
|
||||
import net.gepafin.tendermanagement.config.Translator;
|
||||
import net.gepafin.tendermanagement.constants.GepafinConstant;
|
||||
import net.gepafin.tendermanagement.enums.UserActionContextEnum;
|
||||
import net.gepafin.tendermanagement.enums.UserActionLogsEnum;
|
||||
import net.gepafin.tendermanagement.model.request.CommunicationRequestBean;
|
||||
import net.gepafin.tendermanagement.model.request.UserActionRequest;
|
||||
import net.gepafin.tendermanagement.model.response.ApplicationAmendmentResponse;
|
||||
import net.gepafin.tendermanagement.model.response.CommunicationResponseBean;
|
||||
import net.gepafin.tendermanagement.model.util.Response;
|
||||
import net.gepafin.tendermanagement.service.CommunicationService;
|
||||
import net.gepafin.tendermanagement.util.LoggingUtil;
|
||||
import net.gepafin.tendermanagement.web.rest.api.CommunicationApi;
|
||||
import net.gepafin.tendermanagement.web.rest.api.errors.Status;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
@@ -23,10 +27,16 @@ public class CommunicationController implements CommunicationApi {
|
||||
@Autowired
|
||||
CommunicationService communicationService;
|
||||
|
||||
@Autowired
|
||||
private LoggingUtil loggingUtil;
|
||||
|
||||
@Override
|
||||
public ResponseEntity<Response<CommunicationResponseBean>> addCommentToAmendmentRequest(HttpServletRequest request, CommunicationRequestBean communicationRequestBean,
|
||||
Long amendmentId) {
|
||||
|
||||
/** This code is responsible for creating user action logs for the "Adding comment to amendment request" operation. **/
|
||||
loggingUtil.logUserAction(UserActionRequest.builder().request(request).actionType(UserActionLogsEnum.INSERT).actionContext(UserActionContextEnum.ADD_COMMENT_TO_AMENDMENT_REQUEST).build());
|
||||
|
||||
CommunicationResponseBean communicationResponseBean = communicationService.addCommentToAmendmentRequest(request,communicationRequestBean, amendmentId);
|
||||
return ResponseEntity.status(HttpStatus.CREATED)
|
||||
.body(new Response<>(communicationResponseBean, Status.SUCCESS, Translator.toLocale(GepafinConstant.COMMUNICATION_ADDED_TO_AMENDMENT_REQUEST_SUCCESS)));
|
||||
@@ -34,6 +44,9 @@ public class CommunicationController implements CommunicationApi {
|
||||
@Override
|
||||
public ResponseEntity<Response<ApplicationAmendmentResponse>> getAmendmentComments(HttpServletRequest request,Long amendmentId) {
|
||||
|
||||
/** This code is responsible for creating user action logs for the "getting comment of amendment" operation. **/
|
||||
loggingUtil.logUserAction(UserActionRequest.builder().request(request).actionType(UserActionLogsEnum.VIEW).actionContext(UserActionContextEnum.GET_AMENDMENT_COMMENT).build());
|
||||
|
||||
ApplicationAmendmentResponse response = communicationService.getAmendmentComments(request,amendmentId);
|
||||
return ResponseEntity.ok(new Response<>(response, Status.SUCCESS, Translator.toLocale(GepafinConstant.AMENDMENT_FOUND_SUCCESS)));
|
||||
}
|
||||
@@ -41,6 +54,9 @@ public class CommunicationController implements CommunicationApi {
|
||||
public ResponseEntity<Response<CommunicationResponseBean>> updateCommunicationAmendment(HttpServletRequest request, CommunicationRequestBean communicationRequestBean,
|
||||
Long amendmentId, Long commentId) {
|
||||
|
||||
/** This code is responsible for creating user action logs for the "update communication comment of amendment request" operation. **/
|
||||
loggingUtil.logUserAction(UserActionRequest.builder().request(request).actionType(UserActionLogsEnum.UPDATE).actionContext(UserActionContextEnum.UPDATE_COMMUNICATION_COMMENT).build());
|
||||
|
||||
CommunicationResponseBean communicationResponseBean = communicationService.updateAmendmentComment(request,communicationRequestBean, amendmentId, commentId);
|
||||
return ResponseEntity.status(HttpStatus.OK)
|
||||
.body(new Response<>(communicationResponseBean, Status.SUCCESS, Translator.toLocale(GepafinConstant.COMMENT_UPDATED_SUCCESS_MSG)));
|
||||
@@ -48,6 +64,9 @@ public class CommunicationController implements CommunicationApi {
|
||||
@Override
|
||||
public ResponseEntity<Response<String>> deleteApplicationAmendmentComment(HttpServletRequest request, Long applicationAmendId, Long commentId) {
|
||||
|
||||
/** This code is responsible for creating user action logs for the "Delete communication comment of amendment request" operation. **/
|
||||
loggingUtil.logUserAction(UserActionRequest.builder().request(request).actionType(UserActionLogsEnum.DELETE).actionContext(UserActionContextEnum.DELETE_COMMENT_FROM_AMENDMENT).build());
|
||||
|
||||
String communicationResponseBean = communicationService.deleteComment(request,applicationAmendId, commentId);
|
||||
return ResponseEntity.status(HttpStatus.OK)
|
||||
.body(new Response<>(communicationResponseBean, Status.SUCCESS, Translator.toLocale(GepafinConstant.COMMENT_DELETED_SUCCESS_MSG)));
|
||||
|
||||
Reference in New Issue
Block a user