diff --git a/src/main/java/net/gepafin/tendermanagement/constants/GepafinConstant.java b/src/main/java/net/gepafin/tendermanagement/constants/GepafinConstant.java index 7777325a..03459e12 100644 --- a/src/main/java/net/gepafin/tendermanagement/constants/GepafinConstant.java +++ b/src/main/java/net/gepafin/tendermanagement/constants/GepafinConstant.java @@ -122,5 +122,10 @@ public class GepafinConstant { public static final String VALIDATION_FIELD_NOT_NULL = "validation.field.not_null"; public static final String VALIDATION_FIELD_NOT_EMPTY = "validation.field.not_empty"; public static final String APPLICATION_ALREADY_EXISTS="application.already.exists"; + // public static final String NEXT_FORM_NOT_FOUND = "next.form.not.found"; + // public static final String PREVIOUS_FORM_NOT_FOUND = "previous.form.not.found"; + public static final String CURRENT_FORM_INCOMPLETE = "current.form.incomplete"; + + } diff --git a/src/main/java/net/gepafin/tendermanagement/dao/ApplicationDao.java b/src/main/java/net/gepafin/tendermanagement/dao/ApplicationDao.java index 589b97f2..f1a99e27 100644 --- a/src/main/java/net/gepafin/tendermanagement/dao/ApplicationDao.java +++ b/src/main/java/net/gepafin/tendermanagement/dao/ApplicationDao.java @@ -13,7 +13,7 @@ import net.gepafin.tendermanagement.repositories.ApplicationFormRepository; import net.gepafin.tendermanagement.repositories.ApplicationRepository; import net.gepafin.tendermanagement.service.CallService; import net.gepafin.tendermanagement.service.FormService; -import net.gepafin.tendermanagement.service.UserService; +import net.gepafin.tendermanagement.util.DateTimeUtil; import net.gepafin.tendermanagement.util.Utils; import net.gepafin.tendermanagement.web.rest.api.errors.CustomValidationException; import net.gepafin.tendermanagement.web.rest.api.errors.ResourceNotFoundException; @@ -23,6 +23,7 @@ import org.slf4j.LoggerFactory; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Component; +import java.time.LocalDateTime; import java.util.*; import java.util.stream.Collectors; @@ -31,13 +32,9 @@ public class ApplicationDao { private final Logger log = LoggerFactory.getLogger(ApplicationDao.class); - @Autowired private CallService callService; - @Autowired - private UserService userService; - @Autowired private ApplicationRepository applicationRepository; @@ -159,7 +156,7 @@ public class ApplicationDao { } public ApplicationEntity getApplicationOrCreate(UserEntity userEntity, CallEntity callEntity, FormEntity formEntity) { - ApplicationEntity applicationEntity = applicationRepository.findByUserIdAndCallIdAndIsDeletedFalse(userEntity.getId(), callEntity.getId()); + ApplicationEntity applicationEntity = applicationRepository.findByUserIdAndCallIdAndIsDeletedFalse(userEntity.getId(), callEntity.getId()).orElse(null); if (applicationEntity == null) { validateFormId(formEntity, callEntity); applicationEntity = createApplicationEntity(userEntity, callEntity); @@ -198,7 +195,7 @@ public class ApplicationDao { public ApplicationFormFieldEntity validateApplicationFormField(Long applicationFormFieldId) { Optional applicationFormFieldEntity = applicationFormFieldRepository.findById(applicationFormFieldId); if (applicationFormFieldEntity.isEmpty()) { - throw new CustomValidationException(Status.NOT_FOUND, Translator.toLocale(GepafinConstant.APPLICATION_FORM_FIELD_NOT_FOUND)); + throw new ResourceNotFoundException(Status.NOT_FOUND, Translator.toLocale(GepafinConstant.APPLICATION_FORM_FIELD_NOT_FOUND)); } return applicationFormFieldEntity.get(); } @@ -230,18 +227,16 @@ public class ApplicationDao { } public ApplicationGetResponseBean getApplicationByFormId( Long applicationId,Long formId, UserEntity userEntity) { - - ApplicationEntity applicationEntity=null; List formApplicationResponses = new ArrayList<>(); List formEntities = new ArrayList<>(); - Optional applicationEntity1 = applicationRepository.findById(applicationId); - applicationEntity=applicationEntity1.get(); - if (applicationEntity == null) { - throw new CustomValidationException(Status.BAD_REQUEST,Translator.toLocale(GepafinConstant.APPLICATION_NOT_FOUND_MSG)); - } + ApplicationEntity applicationEntity = applicationRepository.findById(applicationId) + .orElseThrow(() -> new CustomValidationException(Status.BAD_REQUEST, Translator.toLocale(GepafinConstant.APPLICATION_NOT_FOUND_MSG))); + if (formId != null) { FormEntity formEntity = formService.validateForm(formId); - applicationEntity = applicationRepository.findByUserIdAndCallIdAndIsDeletedFalse(userEntity.getId(), formEntity.getCall().getId()); + Optional application = applicationRepository.findByUserIdAndCallIdAndIsDeletedFalse(userEntity.getId(), + formEntity.getCall().getId()); + applicationEntity=application.get(); formEntities.add(formEntity); processForm(formEntity, applicationEntity, formApplicationResponses); } @@ -301,9 +296,26 @@ public class ApplicationDao { return applicationResponse; } public void checkIfApplicationExists(CallEntity call,UserEntity userEntity){ - ApplicationEntity applicationEntity=applicationRepository.findByUserIdAndCallIdAndIsDeletedFalse(userEntity.getId(),call.getId()); - if(applicationEntity!=null){ + Optional applicationEntity=applicationRepository.findByUserIdAndCallIdAndIsDeletedFalse(userEntity.getId(),call.getId()); + if(applicationEntity.isPresent()){ throw new CustomValidationException(Status.BAD_REQUEST,Translator.toLocale(GepafinConstant.APPLICATION_ALREADY_EXISTS)); } } + + + public ApplicationEntity getApplicationByCallAndUser(CallEntity call, UserEntity userEntity) { + return applicationRepository.findByUserIdAndCallIdAndIsDeletedFalse(userEntity.getId(), call.getId()) + .orElseThrow(() -> new ResourceNotFoundException(Status.NOT_FOUND, + Translator.toLocale(GepafinConstant.APPLICATION_NOT_FOUND_MSG))); + + } + + public void updateApplicationStatus(Long applicationId, ApplicationStatusTypeEnum status) { + ApplicationEntity applicationEntity = validateApplication(applicationId); + applicationEntity.setStatus(status.getValue()); + if(status.equals(ApplicationStatusTypeEnum.SUBMIT)) { + applicationEntity.setSubmissionDate(DateTimeUtil.DateServerToUTC(LocalDateTime.now())); + } + saveApplicationEntity(applicationEntity); + } } diff --git a/src/main/java/net/gepafin/tendermanagement/dao/FlowFormDao.java b/src/main/java/net/gepafin/tendermanagement/dao/FlowFormDao.java new file mode 100644 index 00000000..7163f1f6 --- /dev/null +++ b/src/main/java/net/gepafin/tendermanagement/dao/FlowFormDao.java @@ -0,0 +1,255 @@ +package net.gepafin.tendermanagement.dao; + +import java.util.List; +import java.util.Optional; +import java.util.Set; +import java.util.stream.Collectors; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Component; + +import net.gepafin.tendermanagement.config.Translator; +import net.gepafin.tendermanagement.constants.GepafinConstant; +import net.gepafin.tendermanagement.entities.ApplicationEntity; +import net.gepafin.tendermanagement.entities.ApplicationFormEntity; +import net.gepafin.tendermanagement.entities.ApplicationFormFieldEntity; +import net.gepafin.tendermanagement.entities.FlowDataEntity; +import net.gepafin.tendermanagement.entities.FlowEdgesEntity; +import net.gepafin.tendermanagement.entities.FormEntity; +import net.gepafin.tendermanagement.enums.FormActionEnum; +import net.gepafin.tendermanagement.model.response.NextOrPreviousFormResponse; +import net.gepafin.tendermanagement.repositories.ApplicationFormFieldRepository; +import net.gepafin.tendermanagement.repositories.ApplicationFormRepository; +import net.gepafin.tendermanagement.repositories.FlowDataRepository; +import net.gepafin.tendermanagement.repositories.FlowEdgesRepository; +import net.gepafin.tendermanagement.web.rest.api.errors.CustomValidationException; +import net.gepafin.tendermanagement.web.rest.api.errors.ResourceNotFoundException; +import net.gepafin.tendermanagement.web.rest.api.errors.Status; + +@Component +public class FlowFormDao { + + @Autowired + private FlowEdgesRepository flowEdgesRepository; + + @Autowired + private FlowDataRepository flowDataRepository; + + @Autowired + private ApplicationFormFieldRepository applicationFormFieldRepository; + + @Autowired + private ApplicationFormRepository applicationFormRepository; + + +// Long getNextForm(FormEntity currentFormEntity, ApplicationEntity applicationEntity) { +// // vlaidation if next form findout and cuuent from is not fill the give error +// List flowEdgesList = flowEdgesRepository.findBySourceIdAndCallId(currentFormEntity.getId(), applicationEntity.getCall().getId()); +// ApplicationFormEntity applicationFormEntity = applicationFormRepository.findByApplicationIdAndFormId(applicationEntity.getId(), currentFormEntity.getId()); +// if(applicationFormEntity == null) { +// throw new CustomValidationException(Status.VALIDATION_ERROR, +// Translator.toLocale("current form is not fill")); +// } +// if(flowEdgesList.isEmpty()) { +// throw new ResourceNotFoundException(Status.NOT_FOUND, +// Translator.toLocale(GepafinConstant.NEXT_FORM_NOT_FOUND)); +// } else if(flowEdgesList.size() == 1) { +// return flowEdgesList.get(0).getTargetId(); +// } else { +// List nextFormIds = flowEdgesList.stream().map(FlowEdgesEntity::getTargetId).toList(); +// FlowDataEntity flowDataEntity = flowDataRepository.findByFormIdAndCallId(currentFormEntity.getId(), applicationEntity.getCall().getId()); +// +// ApplicationFormFieldEntity applicationFormFieldEntity = applicationFormFieldRepository +// .findByFieldIdAndApplicationFormFormIdAndApplicationFormApplicationId(flowDataEntity.getChoosenField(), +// currentFormEntity.getId(), applicationEntity.getId()).orElseThrow(()-> new ResourceNotFoundException(Status.NOT_FOUND, +// Translator.toLocale(GepafinConstant.NEXT_FORM_NOT_FOUND))); +// +// flowDataEntity = flowDataRepository.findByChoosenValueAndFormIdIn(applicationFormFieldEntity.getFieldValue(), nextFormIds).orElseThrow(()-> new NullPointerException()); +// return flowDataEntity.getFormId(); +// } +// } +// +// +// Long getPreviousForm(FormEntity currentFormEntity, ApplicationEntity applicationEntity) { +// +// // Step 1: Find all edges where the current form is the target (i.e., reverse flow) +// List flowEdgesList = flowEdgesRepository.findByTargetIdAndCallId( +// currentFormEntity.getId(), applicationEntity.getCall().getId()); +// +// if (flowEdgesList.isEmpty()) { +// // If no previous edges are found, return null or handle this case based on your needs +// throw new ResourceNotFoundException(Status.NOT_FOUND, +// Translator.toLocale(GepafinConstant.PREVIOUS_FORM_NOT_FOUND)); +// } +// +// // Step 2: If only one edge exists, return the source (previous) form ID directly have to look into it +// if (flowEdgesList.size() == 1) { +// return flowEdgesList.get(0).getSourceId(); +// } +// List previousFormIds = flowEdgesList.stream().map(FlowEdgesEntity::getSourceId).toList(); +// +// +// // Step 3: Try to find flow data for the current form. If not found, we know it's the last step (or no field filtering is needed). +// List flowDataList = flowDataRepository.findByFormIdInAndCallId( +// previousFormIds, applicationEntity.getCall().getId()); +// +// List fieldValue = flowDataList.stream().map(FlowDataEntity::getChoosenValue).toList(); +// +//// if (flowDataEntity == null || flowDataEntity.getChoosenField() == null) { +//// // If flow data is not found, simply return the first matching previous form +//// return flowEdgesList.get(0).getSourceId(); // You can modify this logic if needed +//// } +// +// // Step 4: Fetch the field value from the application form fields +// Set formList = applicationFormFieldRepository +// .findByFieldValueInAndAndApplicationFormApplicationId( +// fieldValue, applicationEntity.getId()).stream().map(applicationFormFieldEntity->applicationFormFieldEntity.getApplicationForm().getForm()).collect(Collectors.toSet()); +// +// List fieldIds = formList.stream().map(formEntity->getNextForm(formEntity, applicationEntity)).toList(); +// for(Long formId:previousFormIds) { +// fieldIds.contains(formId); +// return formId; +// } +// return null; +//// .orElseThrow(() -> new NullPointerException("Field value not found for the current form and application.")); +// +// +//// // Step 5: Check if there's a matching previous form based on the chosen value +//// FlowDataEntity previousFlowDataEntity = flowDataRepository.findByChoosenValueAndFormIdIn( +//// applicationFormFieldEntity.getFieldValue(), flowEdgesList.stream().map(FlowEdgesEntity::getSourceId).toList()) +//// .orElse(null); // If no matching form is found, return null or the first source form +//// +//// // Step 6: Return the formId of the matching previous form, or the first one if no specific match is found +//// return previousFlowDataEntity != null ? previousFlowDataEntity.getFormId() : flowEdgesList.get(0).getSourceId(); +// } + + + public Long getNextForm(FormEntity currentFormEntity, ApplicationEntity applicationEntity) { + // Validate if the current form has been filled + ApplicationFormEntity applicationFormEntity = applicationFormRepository.findByApplicationIdAndFormId( + applicationEntity.getId(), currentFormEntity.getId()); + + // Retrieve the flow edges for the next forms + List flowEdgesList = flowEdgesRepository.findBySourceIdAndCallId( + currentFormEntity.getId(), applicationEntity.getCall().getId()); + + if (flowEdgesList.isEmpty()) { + return null; +// throw new ResourceNotFoundException(Status.NOT_FOUND, +// Translator.toLocale(GepafinConstant.NEXT_FORM_NOT_FOUND)); + } + + // If only one edge exists, return the target form ID + if (flowEdgesList.size() == 1) { + return flowEdgesList.get(0).getTargetId(); + } + + if (applicationFormEntity == null) { + throw new CustomValidationException(Status.VALIDATION_ERROR, + Translator.toLocale(GepafinConstant.CURRENT_FORM_INCOMPLETE)); + } + + // For multiple edges, find the next form based on the chosen value + List nextFormIds = flowEdgesList.stream() + .map(FlowEdgesEntity::getTargetId) + .toList(); + + // Retrieve the flow data for the current form + FlowDataEntity flowDataEntity = flowDataRepository.findByFormIdAndCallId( + currentFormEntity.getId(), applicationEntity.getCall().getId()); + + // Fetch the application form field related to the chosen field + ApplicationFormFieldEntity applicationFormFieldEntity = applicationFormFieldRepository + .findByFieldIdAndApplicationFormFormIdAndApplicationFormApplicationId( + flowDataEntity.getChoosenField(), currentFormEntity.getId(), applicationEntity.getId()).orElse(null); + + // Find the next form based on the chosen value and return its ID + return flowDataRepository.findByChoosenValueAndFormIdIn( + applicationFormFieldEntity.getFieldValue(), nextFormIds) + .map(FlowDataEntity::getFormId) + .orElse(null); + } + + public Long getPreviousForm(FormEntity currentFormEntity, ApplicationEntity applicationEntity) { + // Retrieve the flow edges for the previous forms + List flowEdgesList = flowEdgesRepository.findByTargetIdAndCallId( + currentFormEntity.getId(), applicationEntity.getCall().getId()); + + if (flowEdgesList.isEmpty()) { + return null; +// throw new ResourceNotFoundException(Status.NOT_FOUND, +// Translator.toLocale(GepafinConstant.PREVIOUS_FORM_NOT_FOUND)); + } + + // If only one edge exists, return the source form ID + if (flowEdgesList.size() == 1) { + return flowEdgesList.get(0).getSourceId(); + } + + // For multiple edges, find the previous form based on the chosen value + List previousFormIds = flowEdgesList.stream() + .map(FlowEdgesEntity::getSourceId) + .toList(); + + // Fetch the flow data based on previous form IDs + List flowDataList = flowDataRepository.findByFormIdInAndCallId( + previousFormIds, applicationEntity.getCall().getId()); + + List chosenValues = flowDataList.stream() + .map(FlowDataEntity::getChoosenValue) + .toList(); + + // Fetch the previous forms based on the chosen field values + Set formList = applicationFormFieldRepository + .findByFieldValueInAndApplicationFormApplicationId(chosenValues, applicationEntity.getId()).stream() + .map(fieldEntity -> fieldEntity.getApplicationForm().getForm()) + .collect(Collectors.toSet()); + + // Find next form IDs recursively for all forms in the formList + List fieldIds = formList.stream() + .map(formEntity -> getNextForm(formEntity, applicationEntity)) + .toList(); + + // Return the first matching previous form ID that corresponds to a next form + return previousFormIds.stream() + .filter(fieldIds::contains) + .findFirst().orElse(null); + } + + public NextOrPreviousFormResponse getnextOrPreviousForm(ApplicationEntity applicationEntity, Long formId, + FormActionEnum action) { + FormEntity fromEntity = null; + if(formId == null) { + NextOrPreviousFormResponse nextOrPreviousFormResponse = new NextOrPreviousFormResponse(); + nextOrPreviousFormResponse.setNextFormId(getDefaultForm(applicationEntity)); + return nextOrPreviousFormResponse; + }else { + fromEntity = Optional + .of(applicationFormRepository.findByApplicationIdAndFormId(applicationEntity.getId(), formId)) + .orElseThrow(() -> new ResourceNotFoundException(Status.NOT_FOUND, + Translator.toLocale(GepafinConstant.FORM_NOT_FOUND))) + .getForm(); + } + + NextOrPreviousFormResponse nextOrPreviousFormResponse = new NextOrPreviousFormResponse(); + if (action.equals(FormActionEnum.NEXT)) { + nextOrPreviousFormResponse.setNextFormId(getNextForm(fromEntity, applicationEntity)); + } else { + nextOrPreviousFormResponse.setPreviousFormId(getPreviousForm(fromEntity, applicationEntity)); + } + return nextOrPreviousFormResponse; + } + + private Long getDefaultForm(ApplicationEntity applicationEntity) { + List applicationFormList = applicationFormRepository.findByApplicationIdOrderByCreatedDateAsc(applicationEntity.getId()); + if(applicationFormList.isEmpty()) { + return applicationEntity.getCall().getInitialForm(); + } + if(applicationFormList.get(applicationFormList.size()-1).getForm().getId().equals(applicationEntity.getCall().getFinalForm())) { + return applicationEntity.getCall().getInitialForm(); + } + return getNextForm(applicationFormList.get(applicationFormList.size()-1).getForm(), applicationEntity); + } + + +} diff --git a/src/main/java/net/gepafin/tendermanagement/dao/FormDao.java b/src/main/java/net/gepafin/tendermanagement/dao/FormDao.java index c20db699..db91f787 100644 --- a/src/main/java/net/gepafin/tendermanagement/dao/FormDao.java +++ b/src/main/java/net/gepafin/tendermanagement/dao/FormDao.java @@ -10,7 +10,6 @@ import net.gepafin.tendermanagement.model.request.FormRequest; import net.gepafin.tendermanagement.model.response.ContentResponseBean; import net.gepafin.tendermanagement.model.response.FormResponseBean; import net.gepafin.tendermanagement.repositories.ApplicationFormRepository; -import net.gepafin.tendermanagement.repositories.ApplicationRepository; import net.gepafin.tendermanagement.repositories.FormRepository; import net.gepafin.tendermanagement.service.CallService; import net.gepafin.tendermanagement.util.DateTimeUtil; @@ -36,9 +35,6 @@ public class FormDao { @Autowired private CallService callService; - @Autowired - private ApplicationRepository applicationRepository; - @Autowired private ApplicationFormRepository applicationFormRepository; diff --git a/src/main/java/net/gepafin/tendermanagement/entities/ApplicationFormEntity.java b/src/main/java/net/gepafin/tendermanagement/entities/ApplicationFormEntity.java index c795d5ef..a6cc56aa 100644 --- a/src/main/java/net/gepafin/tendermanagement/entities/ApplicationFormEntity.java +++ b/src/main/java/net/gepafin/tendermanagement/entities/ApplicationFormEntity.java @@ -3,14 +3,10 @@ package net.gepafin.tendermanagement.entities; import jakarta.persistence.*; import lombok.*; -import java.time.LocalDateTime; @Entity @Table(name = "APPLICATION_FORM") @Data -@NoArgsConstructor -@AllArgsConstructor -@Builder public class ApplicationFormEntity extends BaseEntity { @ManyToOne diff --git a/src/main/java/net/gepafin/tendermanagement/enums/FormActionEnum.java b/src/main/java/net/gepafin/tendermanagement/enums/FormActionEnum.java new file mode 100644 index 00000000..e5a64c59 --- /dev/null +++ b/src/main/java/net/gepafin/tendermanagement/enums/FormActionEnum.java @@ -0,0 +1,20 @@ +package net.gepafin.tendermanagement.enums; + +import com.fasterxml.jackson.annotation.JsonValue; + +public enum FormActionEnum { + + NEXT("NEXT"), + PREVIOUS("PREVIOUS"); + + private String value; + + FormActionEnum(String value) { + this.value = value; + } + + @JsonValue + public String getValue() { + return value; + } +} diff --git a/src/main/java/net/gepafin/tendermanagement/model/response/ApplicationResponseBean.java b/src/main/java/net/gepafin/tendermanagement/model/response/ApplicationResponseBean.java index 6c0a42f8..b9787067 100644 --- a/src/main/java/net/gepafin/tendermanagement/model/response/ApplicationResponseBean.java +++ b/src/main/java/net/gepafin/tendermanagement/model/response/ApplicationResponseBean.java @@ -1,6 +1,5 @@ package net.gepafin.tendermanagement.model.response; -import jakarta.persistence.Column; import lombok.Data; import net.gepafin.tendermanagement.model.BaseBean; diff --git a/src/main/java/net/gepafin/tendermanagement/model/response/NextOrPreviousFormResponse.java b/src/main/java/net/gepafin/tendermanagement/model/response/NextOrPreviousFormResponse.java new file mode 100644 index 00000000..1f7be289 --- /dev/null +++ b/src/main/java/net/gepafin/tendermanagement/model/response/NextOrPreviousFormResponse.java @@ -0,0 +1,12 @@ +package net.gepafin.tendermanagement.model.response; + +import lombok.Data; + +@Data +public class NextOrPreviousFormResponse { + + Long nextFormId; + + Long previousFormId; + +} \ No newline at end of file diff --git a/src/main/java/net/gepafin/tendermanagement/repositories/ApplicationFormFieldRepository.java b/src/main/java/net/gepafin/tendermanagement/repositories/ApplicationFormFieldRepository.java index baac36b2..89c70488 100644 --- a/src/main/java/net/gepafin/tendermanagement/repositories/ApplicationFormFieldRepository.java +++ b/src/main/java/net/gepafin/tendermanagement/repositories/ApplicationFormFieldRepository.java @@ -1,10 +1,12 @@ package net.gepafin.tendermanagement.repositories; import net.gepafin.tendermanagement.entities.ApplicationFormFieldEntity; + import org.springframework.data.jpa.repository.JpaRepository; import org.springframework.stereotype.Repository; import java.util.List; +import java.util.Optional; @Repository public interface ApplicationFormFieldRepository extends JpaRepository { @@ -12,4 +14,14 @@ public interface ApplicationFormFieldRepository extends JpaRepository findByApplicationFormIdIn(List applicationFormIds); public List findByApplicationFormId(Long applicationFormId); + + public Optional findByFieldIdAndApplicationFormFormIdAndApplicationFormApplicationId( + String fieldId, Long formId, Long applicationId); + + public Optional findByFieldValueInAndApplicationFormFormIdInAndApplicationFormApplicationId( + List fieldValues, List previousFormIds, Long applicationId); + + public List findByFieldValueInAndApplicationFormApplicationId( + List fieldValue, Long applicationId); + } diff --git a/src/main/java/net/gepafin/tendermanagement/repositories/ApplicationFormRepository.java b/src/main/java/net/gepafin/tendermanagement/repositories/ApplicationFormRepository.java index f742925b..992eece3 100644 --- a/src/main/java/net/gepafin/tendermanagement/repositories/ApplicationFormRepository.java +++ b/src/main/java/net/gepafin/tendermanagement/repositories/ApplicationFormRepository.java @@ -15,4 +15,6 @@ public interface ApplicationFormRepository extends JpaRepository findByApplicationId(Long applicationId); + public List findByApplicationIdOrderByCreatedDateAsc(Long applicationId); + } diff --git a/src/main/java/net/gepafin/tendermanagement/repositories/ApplicationRepository.java b/src/main/java/net/gepafin/tendermanagement/repositories/ApplicationRepository.java index efdc0655..b32b8f46 100644 --- a/src/main/java/net/gepafin/tendermanagement/repositories/ApplicationRepository.java +++ b/src/main/java/net/gepafin/tendermanagement/repositories/ApplicationRepository.java @@ -13,7 +13,7 @@ import java.util.Optional; @Repository public interface ApplicationRepository extends JpaRepository { - public ApplicationEntity findByUserIdAndCallIdAndIsDeletedFalse(Long userId,Long callId); + public Optional findByUserIdAndCallIdAndIsDeletedFalse(Long userId,Long callId); public List findByUserIdAndIsDeletedFalse(Long userId); diff --git a/src/main/java/net/gepafin/tendermanagement/repositories/FlowDataRepository.java b/src/main/java/net/gepafin/tendermanagement/repositories/FlowDataRepository.java index 0f74d12b..8f752aa9 100644 --- a/src/main/java/net/gepafin/tendermanagement/repositories/FlowDataRepository.java +++ b/src/main/java/net/gepafin/tendermanagement/repositories/FlowDataRepository.java @@ -5,9 +5,16 @@ import org.springframework.data.jpa.repository.JpaRepository; import org.springframework.stereotype.Repository; import java.util.List; +import java.util.Optional; @Repository public interface FlowDataRepository extends JpaRepository { public List findByCallId(Long callId); + + public FlowDataEntity findByFormIdAndCallId(Long formId, Long callId); + + public Optional findByChoosenValueAndFormIdIn(String fieldValue, List nextFormIds); + + public List findByFormIdInAndCallId(List previousFormIds, Long callId); } diff --git a/src/main/java/net/gepafin/tendermanagement/repositories/FlowEdgesRepository.java b/src/main/java/net/gepafin/tendermanagement/repositories/FlowEdgesRepository.java index ef4fbe91..3de65c17 100644 --- a/src/main/java/net/gepafin/tendermanagement/repositories/FlowEdgesRepository.java +++ b/src/main/java/net/gepafin/tendermanagement/repositories/FlowEdgesRepository.java @@ -10,4 +10,8 @@ import java.util.List; public interface FlowEdgesRepository extends JpaRepository { public List findByCallId(Long callId); + + public List findBySourceIdAndCallId(Long sourceId, Long callId); + + public List findByTargetIdAndCallId(Long targetId, Long callId); } diff --git a/src/main/java/net/gepafin/tendermanagement/service/ApplicationService.java b/src/main/java/net/gepafin/tendermanagement/service/ApplicationService.java index 3c5fc6d0..013526ff 100644 --- a/src/main/java/net/gepafin/tendermanagement/service/ApplicationService.java +++ b/src/main/java/net/gepafin/tendermanagement/service/ApplicationService.java @@ -3,10 +3,13 @@ package net.gepafin.tendermanagement.service; import jakarta.servlet.http.HttpServletRequest; import net.gepafin.tendermanagement.entities.ApplicationEntity; import net.gepafin.tendermanagement.model.request.ApplicationRequest; +import net.gepafin.tendermanagement.enums.ApplicationStatusTypeEnum; +import net.gepafin.tendermanagement.enums.FormActionEnum; import net.gepafin.tendermanagement.model.request.ApplicationRequestBean; import net.gepafin.tendermanagement.model.response.ApplicationGetResponseBean; import net.gepafin.tendermanagement.model.response.ApplicationResponse; import net.gepafin.tendermanagement.model.response.ApplicationResponseBean; +import net.gepafin.tendermanagement.model.response.NextOrPreviousFormResponse; import java.util.List; @@ -24,4 +27,7 @@ public interface ApplicationService { public ApplicationResponse createApplication(HttpServletRequest request, ApplicationRequest applicationRequest, Long callId); + public NextOrPreviousFormResponse getnextOrPreviousForm(HttpServletRequest request, Long applicationId, Long formId, FormActionEnum action); + + public void updateApplicationStatus(HttpServletRequest request, Long applicationId, ApplicationStatusTypeEnum status); } diff --git a/src/main/java/net/gepafin/tendermanagement/service/impl/ApplicationServiceImpl.java b/src/main/java/net/gepafin/tendermanagement/service/impl/ApplicationServiceImpl.java index 5952c4ef..c0e7b301 100644 --- a/src/main/java/net/gepafin/tendermanagement/service/impl/ApplicationServiceImpl.java +++ b/src/main/java/net/gepafin/tendermanagement/service/impl/ApplicationServiceImpl.java @@ -2,14 +2,20 @@ package net.gepafin.tendermanagement.service.impl; import jakarta.servlet.http.HttpServletRequest; import net.gepafin.tendermanagement.dao.ApplicationDao; +import net.gepafin.tendermanagement.dao.FlowFormDao; import net.gepafin.tendermanagement.entities.ApplicationEntity; +import net.gepafin.tendermanagement.entities.FormEntity; import net.gepafin.tendermanagement.entities.UserEntity; import net.gepafin.tendermanagement.model.request.ApplicationRequest; +import net.gepafin.tendermanagement.enums.ApplicationStatusTypeEnum; +import net.gepafin.tendermanagement.enums.FormActionEnum; import net.gepafin.tendermanagement.model.request.ApplicationRequestBean; import net.gepafin.tendermanagement.model.response.ApplicationGetResponseBean; import net.gepafin.tendermanagement.model.response.ApplicationResponse; import net.gepafin.tendermanagement.model.response.ApplicationResponseBean; +import net.gepafin.tendermanagement.model.response.NextOrPreviousFormResponse; import net.gepafin.tendermanagement.service.ApplicationService; +import net.gepafin.tendermanagement.service.FormService; import net.gepafin.tendermanagement.util.Validator; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Service; @@ -22,6 +28,12 @@ public class ApplicationServiceImpl implements ApplicationService { @Autowired private ApplicationDao applicationDao; + + @Autowired + private FlowFormDao flowFormDao; + + @Autowired + private FormService formService; @Autowired private Validator validator; @@ -57,6 +69,19 @@ public class ApplicationServiceImpl implements ApplicationService { UserEntity userEntity = validator.validateUser(request); return applicationDao.createApplicationByCallId(applicationRequest,callId,userEntity); } + + @Override + public NextOrPreviousFormResponse getnextOrPreviousForm(HttpServletRequest request, Long applicationId, Long formId, + FormActionEnum action) { + ApplicationEntity applicationEntity = validateApplication(applicationId); + return flowFormDao.getnextOrPreviousForm(applicationEntity, formId, action); + } + + @Override + public void updateApplicationStatus(HttpServletRequest request, Long applicationId, ApplicationStatusTypeEnum status) { + applicationDao.updateApplicationStatus(applicationId, status); + + } @Override @Transactional(readOnly = true) diff --git a/src/main/java/net/gepafin/tendermanagement/web/rest/api/ApplicationApi.java b/src/main/java/net/gepafin/tendermanagement/web/rest/api/ApplicationApi.java index 0966d3d1..85f6e345 100644 --- a/src/main/java/net/gepafin/tendermanagement/web/rest/api/ApplicationApi.java +++ b/src/main/java/net/gepafin/tendermanagement/web/rest/api/ApplicationApi.java @@ -1,5 +1,12 @@ package net.gepafin.tendermanagement.web.rest.api; +import java.util.List; + +import org.springframework.http.MediaType; +import org.springframework.http.ResponseEntity; +import org.springframework.validation.annotation.Validated; +import org.springframework.web.bind.annotation.*; + import io.swagger.v3.oas.annotations.Operation; import io.swagger.v3.oas.annotations.Parameter; import io.swagger.v3.oas.annotations.media.Content; @@ -8,18 +15,15 @@ import io.swagger.v3.oas.annotations.responses.ApiResponse; import jakarta.servlet.http.HttpServletRequest; import jakarta.validation.Valid; import net.gepafin.tendermanagement.model.request.ApplicationRequest; +import net.gepafin.tendermanagement.enums.ApplicationStatusTypeEnum; +import net.gepafin.tendermanagement.enums.FormActionEnum; import net.gepafin.tendermanagement.model.request.ApplicationRequestBean; import net.gepafin.tendermanagement.model.response.ApplicationGetResponseBean; import net.gepafin.tendermanagement.model.response.ApplicationResponse; import net.gepafin.tendermanagement.model.response.ApplicationResponseBean; +import net.gepafin.tendermanagement.model.response.NextOrPreviousFormResponse; import net.gepafin.tendermanagement.model.util.Response; import net.gepafin.tendermanagement.web.rest.api.errors.ErrorConstants; -import org.springframework.http.MediaType; -import org.springframework.http.ResponseEntity; -import org.springframework.validation.annotation.Validated; -import org.springframework.web.bind.annotation.*; - -import java.util.List; @Validated public interface ApplicationApi { @@ -91,5 +95,38 @@ public interface ApplicationApi { @Parameter(description = " Flow request object", required = true) @Valid @RequestBody ApplicationRequest applicationRequest, @Parameter(description = "The call ID", required = true) @PathVariable("callId") Long callId); + + + @Operation(summary = "Api to get an next or previous form by current form id", + responses = { + @ApiResponse(responseCode = "200", description = "OK"), + @ApiResponse(responseCode = "404", description = "Not Found", content = @Content(mediaType = MediaType.APPLICATION_JSON_VALUE, examples = { + @ExampleObject(value = ErrorConstants.NOTFOUND_ERROR_EXAMPLE) })), + @ApiResponse(responseCode = "401", description = "Unauthorized", content = @Content(mediaType = MediaType.APPLICATION_JSON_VALUE, examples = { + @ExampleObject(value = ErrorConstants.UNAUTHORIZED_ERROR_EXAMPLE) })), + @ApiResponse(responseCode = "400", description = "Bad Request", content = @Content(mediaType = MediaType.APPLICATION_JSON_VALUE, examples = { + @ExampleObject(value = ErrorConstants.BADREQUEST_ERROR_EXAMPLE) })) }) + @GetMapping(value = "/{applicationId}/form/next-previous", produces = "application/json") + ResponseEntity> getnextOrPreviousForm(HttpServletRequest request, + @Parameter(description = "The applicaltion id", required = true) @PathVariable("applicationId") Long applicationId, + @Parameter(description = "The form id", required = false) @RequestParam(value = "formId", required = false) Long formId, + @RequestParam("action") FormActionEnum action); + + + @Operation(summary = "Api to update application status", + responses = { + @ApiResponse(responseCode = "200", description = "OK"), + @ApiResponse(responseCode = "404", description = "Not Found", content = @Content(mediaType = MediaType.APPLICATION_JSON_VALUE, examples = { + @ExampleObject(value = ErrorConstants.NOTFOUND_ERROR_EXAMPLE) })), + @ApiResponse(responseCode = "401", description = "Unauthorized", content = @Content(mediaType = MediaType.APPLICATION_JSON_VALUE, examples = { + @ExampleObject(value = ErrorConstants.UNAUTHORIZED_ERROR_EXAMPLE) })), + @ApiResponse(responseCode = "400", description = "Bad Request", content = @Content(mediaType = MediaType.APPLICATION_JSON_VALUE, examples = { + @ExampleObject(value = ErrorConstants.BADREQUEST_ERROR_EXAMPLE) })) }) + @PutMapping(value = "/{applicationId}/status", produces = { "application/json" }) + ResponseEntity> updateApplicationStatus(HttpServletRequest request, + @Parameter(description = "The application id", required = true) @PathVariable("applicationId") Long applicationId, + @Parameter(description = "status", required = true)@RequestParam(value = "status", required = true) ApplicationStatusTypeEnum status); + + } diff --git a/src/main/java/net/gepafin/tendermanagement/web/rest/api/impl/ApplicationApiController.java b/src/main/java/net/gepafin/tendermanagement/web/rest/api/impl/ApplicationApiController.java index 183f54c8..9986412b 100644 --- a/src/main/java/net/gepafin/tendermanagement/web/rest/api/impl/ApplicationApiController.java +++ b/src/main/java/net/gepafin/tendermanagement/web/rest/api/impl/ApplicationApiController.java @@ -4,10 +4,13 @@ import jakarta.servlet.http.HttpServletRequest; import net.gepafin.tendermanagement.config.Translator; import net.gepafin.tendermanagement.constants.GepafinConstant; import net.gepafin.tendermanagement.model.request.ApplicationRequest; +import net.gepafin.tendermanagement.enums.ApplicationStatusTypeEnum; +import net.gepafin.tendermanagement.enums.FormActionEnum; import net.gepafin.tendermanagement.model.request.ApplicationRequestBean; import net.gepafin.tendermanagement.model.response.ApplicationGetResponseBean; import net.gepafin.tendermanagement.model.response.ApplicationResponse; import net.gepafin.tendermanagement.model.response.ApplicationResponseBean; +import net.gepafin.tendermanagement.model.response.NextOrPreviousFormResponse; import net.gepafin.tendermanagement.model.util.Response; import net.gepafin.tendermanagement.service.ApplicationService; import net.gepafin.tendermanagement.web.rest.api.ApplicationApi; @@ -69,4 +72,21 @@ public class ApplicationApiController implements ApplicationApi { return ResponseEntity.status(HttpStatus.OK) .body(new Response<>(applications, Status.SUCCESS, Translator.toLocale(GepafinConstant.GET_APPLICATION_SUCCESS_MSG))); } + + @Override + public ResponseEntity> getnextOrPreviousForm(HttpServletRequest request,Long applicationId, + Long formId, FormActionEnum action) { + NextOrPreviousFormResponse data = applicationService.getnextOrPreviousForm(request, applicationId, formId, action); + log.info("Get Next Or Previous Form "); + return ResponseEntity.status(HttpStatus.OK) + .body(new Response<>(data, Status.SUCCESS, Translator.toLocale(GepafinConstant.GET_APPLICATION_SUCCESS_MSG))); + } + + @Override + public ResponseEntity> updateApplicationStatus(HttpServletRequest request, Long applicationId, + ApplicationStatusTypeEnum status) { + applicationService.updateApplicationStatus(request, applicationId, status); + return ResponseEntity.status(HttpStatus.OK) + .body(new Response<>(null, Status.SUCCESS, Translator.toLocale(GepafinConstant.GET_APPLICATION_SUCCESS_MSG))); + } } diff --git a/src/main/resources/message_en.properties b/src/main/resources/message_en.properties index 3b7c11df..454403f4 100644 --- a/src/main/resources/message_en.properties +++ b/src/main/resources/message_en.properties @@ -158,3 +158,4 @@ validation.field.pattern=Field {0} does not match the required pattern. validation.field.not_null=Field {0} must not be null. validation.field.not_empty=Field {0} must not be empty. +current.form.incomplete=Current form is not filled. diff --git a/src/main/resources/message_it.properties b/src/main/resources/message_it.properties index cd32956d..c9219f27 100644 --- a/src/main/resources/message_it.properties +++ b/src/main/resources/message_it.properties @@ -152,4 +152,5 @@ validation.field.min_length=Il campo {0} deve essere lungo almeno {1} caratteri. validation.field.max_length=Il campo {0} deve essere lungo al massimo {1} caratteri. validation.field.pattern=Il campo {0} non corrisponde al modello richiesto. validation.field.not_null=Il campo {0} non deve essere nullo. -validation.field.not_empty=Il campo {0} non deve essere vuoto. \ No newline at end of file +validation.field.not_empty=Il campo {0} non deve essere vuoto. +current.form.incomplete=il modulo corrente non è compilato \ No newline at end of file