Resolved Conflicts

This commit is contained in:
rajesh
2025-03-07 13:43:21 +05:30
14 changed files with 291 additions and 8 deletions

View File

@@ -487,6 +487,7 @@ public class GepafinConstant {
public static final String DATA="data";
public static final String FILE_SELECT = "fileselect";
public static final String INVALID_LIMIT = "error.invalid.limit";
public static final String PREFERRED_CALL_ID="preferredCallId";
public static final String REGION_ID="regionId";

View File

@@ -15,6 +15,10 @@ import java.util.stream.Collectors;
import java.util.zip.ZipEntry;
import java.util.zip.ZipOutputStream;
import jakarta.persistence.criteria.CriteriaBuilder;
import jakarta.persistence.criteria.Expression;
import jakarta.persistence.criteria.Predicate;
import jakarta.persistence.criteria.Root;
import jakarta.persistence.criteria.*;
import jakarta.servlet.http.HttpServletRequest;
import net.gepafin.tendermanagement.entities.*;
@@ -805,6 +809,30 @@ public class CallDao {
} else {
calls = callRepository.findByStatusInAndHubId(callStatusList, user.getHub().getId());
}
LocalDateTime now = LocalDateTime.now();
for (CallEntity call : calls) {
CallEntity oldCallEntity = Utils.getClonedEntityForData(call);
if (CallStatusEnum.PUBLISH.getValue().equals(call.getStatus()) &&
call.getEndDate() != null && call.getEndTime() != null) {
LocalDateTime callEndDateTime = LocalDateTime.of(LocalDate.from(call.getEndDate()), call.getEndTime());
if (callEndDateTime.isBefore(now)) {
call.setStatus(CallStatusEnum.EXPIRED.getValue());
callRepository.save(call);
}
if (Boolean.FALSE.equals(oldCallEntity.getStatus().equals(call.getStatus()))) {
loggingUtil.logUserAction(UserActionRequest.builder()
.request(request)
.actionType(UserActionLogsEnum.UPDATE)
.actionContext(UserActionContextEnum.UPDATE_EXPIRED_CALL)
.build());
/** This code is responsible for adding a version history log for the "update call status to EXPIRED" operation **/
loggingUtil.addVersionHistory(VersionHistoryRequest.builder().request(request).actionType(VersionActionTypeEnum.UPDATE).oldData(oldCallEntity).newData(call).build());
}
}
}
List<Long> callIds = calls.stream().map(CallEntity::getId).collect(Collectors.toList());
Map<String, BeneficiaryPreferredCallEntity> preferredCallsMap =
getBeneficiaryPreferredCallsForUser(request,user, callIds, companyId);
@@ -981,7 +1009,7 @@ public class CallDao {
Translator.toLocale(GepafinConstant.COMPANY_ID_REQUIRED_FOR_PREFERRED_CALL)
);
}
Specification<CallEntity> spec = search(user, callPageableRequestBean);
Specification<CallEntity> spec = search(request,user, callPageableRequestBean);
Page<CallEntity> entityPage;
if (Boolean.TRUE.equals(onlyPreferredCall)) {
validator.validateUserWithCompany(request, companyId);
@@ -1028,10 +1056,10 @@ public class CallDao {
return pageableResponseBean;
}
public Specification<CallEntity> search(UserEntity userEntity, CallPageableRequestBean callPageableRequestBean) {
public Specification<CallEntity> search(HttpServletRequest request,UserEntity userEntity, CallPageableRequestBean callPageableRequestBean) {
return (root, query, criteriaBuilder) -> {
List<Predicate> predicates = getPredicates(callPageableRequestBean, criteriaBuilder, root, userEntity);
List<Predicate> predicates = getPredicates(request,callPageableRequestBean, criteriaBuilder, root, userEntity);
SortBy sortBy = new SortBy(GepafinConstant.CREATED_DATE, true);
if (callPageableRequestBean.getGlobalFilters() != null
@@ -1054,9 +1082,9 @@ public class CallDao {
}
private List<Predicate> getPredicates(CallPageableRequestBean callPageableRequestBean,
private List<Predicate> getPredicates(HttpServletRequest request,CallPageableRequestBean callPageableRequestBean,
CriteriaBuilder criteriaBuilder, Root<CallEntity> root, UserEntity userEntity) {
expirePublishedCalls(request);
Integer year = null;
String search = null;
Map<String, FilterCriteria> filters = new HashMap<>();
@@ -1112,11 +1140,59 @@ public class CallDao {
applyFilters(root, criteriaBuilder, predicates, filters);
predicates.add(criteriaBuilder.equal(root.get(GepafinConstant.HUB).get(GepafinConstant.ID), userEntity.getHub().getId()));
return predicates;
}
public void expirePublishedCalls(HttpServletRequest request) {
List<CallEntity> expiredCalls = callRepository.findAll((root, query, criteriaBuilder) -> {
Predicate isPublished = criteriaBuilder.equal(root.get(GepafinConstant.STATUS), CallStatusEnum.PUBLISH.name());
// Concatenate date and time as a single string
Expression<String> dateTimeString = criteriaBuilder.concat(
root.get(GepafinConstant.END_DATE),
criteriaBuilder.literal(" ") // Space between date and time
);
Expression<String> fullDateTimeString = criteriaBuilder.concat(dateTimeString, root.get(GepafinConstant.END_TIME));
// Convert the concatenated string into TIMESTAMP
Expression<LocalDateTime> endDateTime = criteriaBuilder.function(
"to_timestamp",
LocalDateTime.class,
fullDateTimeString,
criteriaBuilder.literal("YYYY-MM-DD HH24:MI:SS")
);
Predicate isExpired = criteriaBuilder.lessThan(endDateTime, LocalDateTime.now());
return criteriaBuilder.and(isPublished, isExpired);
});
if (!expiredCalls.isEmpty()) {
for (CallEntity call : expiredCalls) {
CallEntity oldCallEntity = Utils.getClonedEntityForData(call); // Clone before modification
call.setStatus(CallStatusEnum.EXPIRED.getValue());
if (!oldCallEntity.getStatus().equals(call.getStatus())) {
// Log user action
loggingUtil.logUserAction(UserActionRequest.builder()
.request(request)
.actionType(UserActionLogsEnum.UPDATE)
.actionContext(UserActionContextEnum.UPDATE_EXPIRED_CALL)
.build());
// Add version history log
loggingUtil.addVersionHistory(VersionHistoryRequest.builder()
.request(request)
.actionType(VersionActionTypeEnum.UPDATE)
.oldData(oldCallEntity)
.newData(call)
.build());
}
}
callRepository.saveAll(expiredCalls); // Save all modified calls at once
}
}
private void applyFilters(Root<?> root, CriteriaBuilder criteriaBuilder, List<Predicate> predicates, Map<String, FilterCriteria> filters) {
if (Boolean.FALSE.equals(filters.isEmpty())) {
for (Map.Entry<String, FilterCriteria> entry : filters.entrySet()) {

View File

@@ -1,23 +1,33 @@
package net.gepafin.tendermanagement.dao;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.springframework.data.domain.Pageable; // Correct package
import java.util.EnumSet;
import java.util.List;
import java.util.Map;
import jakarta.servlet.http.HttpServletRequest;
import lombok.extern.log4j.Log4j2;
import net.gepafin.tendermanagement.entities.*;
import net.gepafin.tendermanagement.enums.ApplicationStatusTypeEnum;
import net.gepafin.tendermanagement.enums.UserCompanyDelegationStatusEnum;
import net.gepafin.tendermanagement.model.request.LimitRequest;
import net.gepafin.tendermanagement.model.response.VatCheckResponseBean;
import net.gepafin.tendermanagement.repositories.*;
import net.gepafin.tendermanagement.service.CompanyService;
import net.gepafin.tendermanagement.enums.VersionActionTypeEnum;
import net.gepafin.tendermanagement.model.request.VersionHistoryRequest;
import net.gepafin.tendermanagement.repositories.ApplicationRepository;
import net.gepafin.tendermanagement.repositories.FaqRepository;
import net.gepafin.tendermanagement.service.feignClient.VatCheckService;
import net.gepafin.tendermanagement.util.LoggingUtil;
import net.gepafin.tendermanagement.web.rest.api.errors.*;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.domain.Sort;
import org.springframework.stereotype.Component;
import net.gepafin.tendermanagement.config.Translator;
@@ -27,9 +37,11 @@ import net.gepafin.tendermanagement.model.response.CompanyResponse;
import net.gepafin.tendermanagement.service.UserService;
import net.gepafin.tendermanagement.util.Utils;
import static net.gepafin.tendermanagement.util.Utils.convertObjectToJsonString;
import static net.gepafin.tendermanagement.util.Utils.setIfUpdated;
@Component
@Log4j2
public class CompanyDao {
@Autowired
@@ -60,6 +72,13 @@ public class CompanyDao {
@Autowired
private HttpServletRequest request;
@Autowired
private VatCheckService vatCheckService; // Service to call VAT API
private static final String NOT_FOUND_JSON = "{\"data\": \"not found\"}";
public CompanyResponse createCompany(UserEntity userEntity, CompanyRequest companyRequest) {
CompanyEntity existingCompany = companyRepository.findByVatNumberAndHubId(companyRequest.getVatNumber(), userEntity.getHub().getId());
@@ -410,4 +429,123 @@ public class CompanyDao {
VersionHistoryRequest.builder().request(request).actionType(VersionActionTypeEnum.SOFT_DELETE).oldData(oldUserWithCompanyData).newData(existingRelation).build());
}
public void updateMissingVatCheckResponses(HttpServletRequest request, LimitRequest limitRequest) {
long limit = limitRequest.getLimit();
if (limit <= 0 || limit > 3000) {
log.error("Invalid limit: {}. Limit should be between 1 and 3000.", limit);
throw new CustomValidationException(Status.VALIDATION_ERROR,
Translator.toLocale(GepafinConstant.INVALID_LIMIT));
}
int successfulUpdates = 0;
int failedUpdates = 0;
int invalidVatNumbers = 0;
Pageable pageable = PageRequest.of(0, (int) limit, Sort.by("id").ascending());
Page<CompanyEntity> companyPage = companyRepository.findCompaniesWithMissingVatCheck(pageable);
List<CompanyEntity> companies = companyPage.getContent();
if (companies.isEmpty()) {
log.info("No companies found with missing VAT check responses.");
return;
}
log.info("Processing {} companies with missing VAT check responses...", companies.size());
for (CompanyEntity company : companies) {
try {
log.info("Processing company ID: {} with VAT number: {}", company.getId(), company.getVatNumber());
VatCheckResponseBean vatResponse = companyService.checkVatNumber(request, company.getVatNumber());
CompanyEntity oldCompanyData = Utils.getClonedEntityForData(company);
if (vatResponse != null && vatResponse.getVatCheckResponse() != null) {
// Convert response to JSON and update the JSON field
String jsonResponse = Utils.convertMapIntoJsonString(vatResponse.getVatCheckResponse());
company.setJson(jsonResponse);
log.info("Company ID {}: JSON field updated successfully.", company.getId());
// Extract and set codiceAteco field
updateCodiceAtecoField(company);
successfulUpdates++;
} else {
company.setJson(NOT_FOUND_JSON);
invalidVatNumbers++;
log.warn("Company ID {}: Invalid or null VAT check response. JSON set to '{}'", company.getId(), NOT_FOUND_JSON);
}
// Adding version history log
/** This code is responsible for adding a version history log for the "Update MissingVatCheckResponses" operation. **/
loggingUtil.addVersionHistory(
VersionHistoryRequest.builder()
.request(request)
.actionType(VersionActionTypeEnum.UPDATE)
.oldData(oldCompanyData)
.newData(company)
.build());
} catch (Exception e) {
failedUpdates++;
log.error("Error updating VAT check response for company ID {}: {}", company.getId(), e.getMessage(), e);
}
}
companyRepository.saveAll(companies);
log.info("VAT check update completed. Limit: {} | Successful: {} | Invalid VAT numbers: {} | Failed: {}",
limit, successfulUpdates, invalidVatNumbers, failedUpdates);
}
private void updateCodiceAtecoField(CompanyEntity company) {
Map<String, Object> vatCheckResponse = Utils.convertJsonStringToMap(company.getJson());
if (vatCheckResponse != null && vatCheckResponse.containsKey("data")) {
Object dataObj = vatCheckResponse.get("data");
if (dataObj instanceof Map) {
Map<String, Object> dataMap = (Map<String, Object>) dataObj;
log.info("Company ID {}: Available keys inside 'data' -> {}", company.getId(), dataMap.keySet());
if (dataMap.containsKey("dettaglio")) {
Object dettaglioObj = dataMap.get("dettaglio");
if (dettaglioObj instanceof Map) {
Map<String, Object> dettaglio = (Map<String, Object>) dettaglioObj;
if (dettaglio.containsKey("codice_ateco")) {
Object codiceAtecoObj = dettaglio.get("codice_ateco");
if (codiceAtecoObj instanceof String) {
String codiceAteco = (String) codiceAtecoObj;
if (codiceAteco != null && !codiceAteco.isEmpty()) {
company.setCodiceAteco(codiceAteco);
log.info("Company ID {}: codiceAteco updated to {}", company.getId(), codiceAteco);
} else {
log.warn("Company ID {}: codiceAteco is null or empty in the response.", company.getId());
}
} else {
log.warn("Company ID {}: 'codice_ateco' is not a string, actual type: {}", company.getId(), codiceAtecoObj.getClass());
}
} else {
log.warn("Company ID {}: 'dettaglio' does not contain 'codice_ateco' key.", company.getId());
}
} else {
log.warn("Company ID {}: 'dettaglio' is not a Map, actual type: {}", company.getId(), dettaglioObj.getClass());
}
} else {
log.warn("Company ID {}: 'dettaglio' section is missing inside 'data'!", company.getId());
}
} else {
log.warn("Company ID {}: 'data' is not a Map, actual type: {}", company.getId(), dataObj.getClass());
}
} else {
log.warn("Company ID {}: 'data' section missing in the JSON response.", company.getId());
}
}
}

View File

@@ -65,6 +65,7 @@ public enum UserActionContextEnum {
CHECK_COMPANY_VAT_NUMBER("CHECK_COMPANY_VAT_NUMBER"),
GET_COMPANY_BY_USER("GET_COMPANY_BY_USER"),
REMOVE_COMPANY_FROM_USER("REMOVE_COMPANY_FROM_USER"),
UPDATE_COMPANY_JSON("UPDATE_COMPANY_JSON"),
/** LookUpData action context **/
CREATE_LOOKUP_DATA("CREATE_LOOKUP_DATA"),
@@ -213,7 +214,8 @@ public enum UserActionContextEnum {
GET_ALL_APPLICATION_AMENDMENT_BY_PAGINATION("GET_ALL_APPLICATION_AMENDMENT_BY_PAGINATION"),
GET_ALL_USER_ACTION_BY_PAGINATION("GET_ALL_USER_ACTION_BY_PAGINATION"),
GET_ALL_USER_BY_PAGINATION("GET_ALL_USER_BY_PAGINATION"),
UPDATE_CALL_END_DATE_AND_TIME("UPDATE_CALL_END_DATE_AND_TIME");
UPDATE_CALL_END_DATE_AND_TIME("UPDATE_CALL_END_DATE_AND_TIME"),
UPDATE_EXPIRED_CALL("UPDATE_EXPIRED_CALL") ;
private final String value;

View File

@@ -0,0 +1,8 @@
package net.gepafin.tendermanagement.model.request;
import lombok.Data;
@Data
public class LimitRequest {
private Long limit;
}

View File

@@ -1,7 +1,10 @@
package net.gepafin.tendermanagement.repositories;
import org.springframework.data.domain.Pageable;
import java.util.List;
import org.springframework.data.domain.Page;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.data.jpa.repository.Query;
import org.springframework.data.repository.query.Param;
@@ -21,5 +24,12 @@ public interface CompanyRepository extends JpaRepository<CompanyEntity, Long> {
CompanyEntity findByVatNumberAndHubId(String vatNumber, Long hubId);
@Query("""
SELECT c FROM CompanyEntity c
WHERE c.vatNumber IS NOT NULL
AND (c.json IS NULL OR c.json = '')
""")
Page<CompanyEntity> findCompaniesWithMissingVatCheck(Pageable pageable);
}

View File

@@ -4,6 +4,7 @@ import java.io.ByteArrayOutputStream;
import java.util.List;
import java.util.Map;
import net.gepafin.tendermanagement.model.request.LimitRequest;
import net.gepafin.tendermanagement.model.response.VatCheckResponseBean;
import org.springframework.web.multipart.MultipartFile;
@@ -45,4 +46,6 @@ public interface CompanyService {
UserWithCompanyEntity getUserWithCompanyEntity(Long userId,Long companyId);
void removeCompanyFromList(HttpServletRequest request, Long companyId);
void updateMissingVatCheckResponses(HttpServletRequest request, LimitRequest limitRequest);
}

View File

@@ -61,7 +61,7 @@ public class CallServiceImpl implements CallService {
}
@Override
@Transactional(readOnly = true)
@Transactional(rollbackFor = Exception.class)
public List<CallDetailsResponseBean> getAllCalls(HttpServletRequest request,Long companyId,Boolean onlyPreferredCall) {
UserEntity user = validator.validateUser(request);
return callDao.getAllCalls(request,user,companyId,onlyPreferredCall);
@@ -104,6 +104,7 @@ public class CallServiceImpl implements CallService {
}
@Override
@Transactional(rollbackFor = Exception.class)
public PageableResponseBean<List<CallDetailsResponseBean>> getAllCallsByPagination(HttpServletRequest request,Long companyId , Boolean onlyPreferredCall, CallPageableRequestBean callPageableRequestBean) {
UserEntity user = validator.validateUser(request);
return callDao.getAllCallsByPagination(request,user,companyId,onlyPreferredCall,callPageableRequestBean);

View File

@@ -4,6 +4,7 @@ import java.io.ByteArrayOutputStream;
import java.util.List;
import java.util.Map;
import net.gepafin.tendermanagement.model.request.LimitRequest;
import net.gepafin.tendermanagement.model.response.VatCheckResponseBean;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
@@ -130,4 +131,10 @@ public class CompanyServiceImpl implements CompanyService {
UserEntity userEntity =validator.validateUser(request);
companyDao.removeCompanyFromList(userEntity, companyId);
}
@Override
public void updateMissingVatCheckResponses(HttpServletRequest request, LimitRequest limitRequest) {
UserEntity userEntity =validator.validateUser(request);
companyDao.updateMissingVatCheckResponses(request, limitRequest);
}
}

View File

@@ -788,4 +788,12 @@ public class Utils {
public static boolean isValidBoolean(String value) {
return "true".equalsIgnoreCase(value) || "false".equalsIgnoreCase(value);
}
public static Map<String, Object> convertJsonStringToMap(String jsonString) {
try {
return mapper.readValue(jsonString, Map.class);
} catch (Exception e) {
e.printStackTrace(); // Handle the exception
return null;
}
}
}

View File

@@ -3,9 +3,11 @@ package net.gepafin.tendermanagement.web.rest.api;
import java.util.List;
import java.util.Map;
import net.gepafin.tendermanagement.model.request.LimitRequest;
import net.gepafin.tendermanagement.model.response.VatCheckResponseBean;
import org.springframework.http.MediaType;
import org.springframework.http.ResponseEntity;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.web.bind.annotation.DeleteMapping;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
@@ -155,4 +157,16 @@ public interface CompanyApi {
ResponseEntity<Response<Void>> removeCompanyFromList(HttpServletRequest request,
@Parameter(description = "The company id", required = true) @PathVariable("companyId") Long companyId);
@Operation(summary = "Api to update company with no data through script", 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) })) })
@PostMapping(value = "/updateCompanyJson", produces = { "application/json" })
@PreAuthorize("hasRole('ROLE_SUPER_ADMIN') ")
ResponseEntity<Response<Void>> updateMissingVatCheckResponses(HttpServletRequest request,
@Parameter(description = "Limit request object ", required = true) @RequestBody LimitRequest limitRequest);
}

View File

@@ -6,6 +6,7 @@ import java.util.Map;
import net.gepafin.tendermanagement.enums.UserActionContextEnum;
import net.gepafin.tendermanagement.enums.UserActionLogsEnum;
import net.gepafin.tendermanagement.model.request.LimitRequest;
import net.gepafin.tendermanagement.model.request.UserActionRequest;
import net.gepafin.tendermanagement.model.response.VatCheckResponseBean;
import net.gepafin.tendermanagement.util.LoggingUtil;
@@ -188,4 +189,16 @@ public class CompanyApiController implements CompanyApi{
return ResponseEntity.status(HttpStatus.OK)
.body(new Response<>(null, Status.SUCCESS, Translator.toLocale(GepafinConstant.COMPANY_DELETE_SUCCESS_MSG)));
}
@Override
public ResponseEntity<Response<Void>> updateMissingVatCheckResponses(HttpServletRequest request, LimitRequest limitRequest) {
log.info("Api to update company json field");
/** This code is responsible for creating user action logs for the "Update company json field" operation. **/
loggingUtil.logUserAction(UserActionRequest.builder().request(request).actionType(UserActionLogsEnum.UPDATE).actionContext(UserActionContextEnum.UPDATE_COMPANY_JSON).build());
companyService.updateMissingVatCheckResponses(request, limitRequest);
return ResponseEntity.status(HttpStatus.OK)
.body(new Response<>(null, Status.SUCCESS, Translator.toLocale(GepafinConstant.COMPANY_UPDATED_SUCCESS_MSG)));
}
}