Commit b2a0d20e authored by Anastasios Poimenidis's avatar Anastasios Poimenidis
Browse files

fix: introduce logic with DTOs and Responses in Individual module

parent d8eaffd0
Loading
Loading
Loading
Loading
Loading
+1 −1
Original line number Diff line number Diff line
@@ -196,7 +196,7 @@
    <dependency>
      <groupId>org.etsi.osl.hypo.api</groupId>
      <artifactId>tmf.schema</artifactId>
      <version>2.6.1</version>
      <version>2.7.1</version>
    </dependency>

    <dependency>
+8 −0
Original line number Diff line number Diff line
package org.etsi.osl.hypo.api.tmf.party.api.mapper;

import org.etsi.osl.hypo.api.tmf.common.schema.RelatedPartyEntity;
import org.etsi.osl.hypo.api.tmf.party.individual.model.IndividualDTO;
import org.etsi.osl.hypo.api.tmf.party.individual.model.IndividualResponse;
import org.etsi.osl.hypo.api.tmf.party.individual.schema.Individual;
import org.etsi.osl.hypo.api.tmf.party.organization.model.OrganizationDTO;
import org.etsi.osl.hypo.api.tmf.party.organization.model.OrganizationResponse;
@@ -38,6 +40,12 @@ public interface OrganizationMapper {
    @BeanMapping(nullValuePropertyMappingStrategy = NullValuePropertyMappingStrategy.IGNORE)
    Organization cloneOrganization(Organization organization);

    Individual individualDTOtoEntity(IndividualDTO individualDTO);

    IndividualResponse individualEntityToResponse(Individual individual);

    IndividualDTO individualResponseToDTO(IndividualResponse individualResponse);

    @Mapping(target = "entityId", ignore = true)
    @Mapping(target = "taxExemptionCertificate.attachment.entityId", ignore = true)
    @Mapping(target = "contactMedium.mediumCharacteristic.entityId", ignore = true)
+29 −22
Original line number Diff line number Diff line
@@ -5,7 +5,6 @@ import static jakarta.ws.rs.core.MediaType.APPLICATION_JSON;
import io.quarkus.security.Authenticated;
import io.quarkus.security.credential.TokenCredential;
import io.quarkus.security.identity.SecurityIdentity;
import jakarta.validation.Valid;
import jakarta.ws.rs.Consumes;
import jakarta.ws.rs.DELETE;
import jakarta.ws.rs.GET;
@@ -17,6 +16,7 @@ import jakarta.ws.rs.core.Context;
import jakarta.ws.rs.core.MediaType;
import jakarta.ws.rs.core.Response;
import jakarta.ws.rs.core.UriInfo;
import java.util.List;
import java.util.Map;
import org.eclipse.microprofile.openapi.annotations.Operation;
import org.eclipse.microprofile.openapi.annotations.enums.SchemaType;
@@ -27,6 +27,8 @@ import org.eclipse.microprofile.openapi.annotations.tags.Tag;
import org.etsi.osl.hypo.api.tmf.common.api.services.UtilService;
import org.etsi.osl.hypo.api.tmf.common.model.ErrorMessage;
import org.etsi.osl.hypo.api.tmf.party.api.services.IndividualService;
import org.etsi.osl.hypo.api.tmf.party.individual.model.IndividualDTO;
import org.etsi.osl.hypo.api.tmf.party.individual.model.IndividualResponse;
import org.etsi.osl.hypo.api.tmf.party.individual.schema.ApplicationProperties;
import org.etsi.osl.hypo.api.tmf.party.individual.schema.Individual;
import org.jboss.logging.Logger;
@@ -61,7 +63,7 @@ public class IndividualResource {
            content =
                    @Content(
                            mediaType = APPLICATION_JSON,
                            schema = @Schema(implementation = Individual.class)))
                            schema = @Schema(implementation = IndividualResponse.class)))
    @APIResponse(responseCode = "400", description = "Bad Request")
    @APIResponse(
            responseCode = "500",
@@ -70,25 +72,27 @@ public class IndividualResource {
                    @Content(
                            mediaType = APPLICATION_JSON,
                            schema = @Schema(implementation = ErrorMessage.class)))
    public Response createIndividual(@Valid Individual individualRequest) {

    public Response createIndividual(IndividualDTO individualRequest) {
        logger.infof(
                "POST Individual Request received for individual name: %s",
                individualRequest.getFullName());
        String authToken = "";

        if (securityIdentity.getCredential(TokenCredential.class) != null) {
            authToken = securityIdentity.getCredential(TokenCredential.class).getToken();
        }
        logger.debugf("CreateIndividual Request : %s", individualRequest.toString());
        Individual createdIndividual = individualService.createIndividual(individualRequest, authToken);
        IndividualResponse createdIndividual =
                individualService.createIndividual(individualRequest, authToken);
        logger.infof(
                "CreateIndividual Response with name: %s and id: %s",
                createdIndividual.getId(), createdIndividual.getFullName());
                "POST Individual Request SUCCESS: Response with name: %s and id: %s",
                createdIndividual.getFullName(), createdIndividual.getId());

        return Response.ok(createdIndividual).status(Response.Status.CREATED).build();
    }

    @GET
    @Produces(MediaType.APPLICATION_JSON)
    @Consumes(MediaType.APPLICATION_JSON)
    @Operation(
            summary = "List or find all Individual objects",
            description = "This operation list or find Individual entities.")
@@ -98,16 +102,19 @@ public class IndividualResource {
            content =
                    @Content(
                            mediaType = APPLICATION_JSON,
                            schema = @Schema(implementation = Individual.class, type = SchemaType.ARRAY)))
                            schema = @Schema(implementation = IndividualResponse.class, type = SchemaType.ARRAY)))
    public Response getAll(@RestQuery String fields, @Context UriInfo uriInfo) {
        logger.infof("GET all Individual Request received");
        Map<String, String> criteriaParams = UtilService.getRequestedCriteriaForFiltering(uriInfo);
        return Response.ok(individualService.getByCriteria(fields, criteriaParams)).build();
        List<IndividualResponse> individualResponses =
                individualService.getByCriteria(fields, criteriaParams);
        logger.infof("GET all Individual SUCCESS received");
        return Response.ok(individualResponses).build();
    }

    @GET
    @Path("/{id}")
    @Produces(MediaType.APPLICATION_JSON)
    @Consumes(MediaType.APPLICATION_JSON)
    @Operation(
            summary = "Retrieves a Individual by ID",
            description =
@@ -118,7 +125,7 @@ public class IndividualResource {
            content =
                    @Content(
                            mediaType = APPLICATION_JSON,
                            schema = @Schema(implementation = Individual.class)))
                            schema = @Schema(implementation = IndividualResponse.class)))
    @APIResponse(
            responseCode = "404",
            description = "Not Found",
@@ -127,11 +134,11 @@ public class IndividualResource {
                            mediaType = APPLICATION_JSON,
                            schema = @Schema(implementation = ErrorMessage.class)))
    public Response getById(@RestPath String id, @RestQuery String fields, @Context UriInfo uriInfo) {
        logger.infof("Get Request: individual with id : %s", id);
        logger.infof("GET Request: individual with id : %s", id);
        Map<String, String> criteriaParams = UtilService.getRequestedCriteriaForFiltering(uriInfo);
        Individual retrievedIndividual =
        IndividualResponse retrievedIndividual =
                individualService.getByIdAndCriteria(id, fields, criteriaParams, 1);
        logger.infof("Get Response for id %s:", id);
        logger.infof("GET SUCCESS: Response for id %s:", id);
        return Response.ok(retrievedIndividual).build();
    }

@@ -146,7 +153,7 @@ public class IndividualResource {
            content =
                    @Content(
                            mediaType = APPLICATION_JSON,
                            schema = @Schema(implementation = Individual.class)))
                            schema = @Schema(implementation = IndividualResponse.class)))
    @APIResponse(
            responseCode = "400",
            description = "Bad Request",
@@ -168,17 +175,17 @@ public class IndividualResource {
                    @Content(
                            mediaType = APPLICATION_JSON,
                            schema = @Schema(implementation = ErrorMessage.class)))
    public Response update(@Valid Individual individualRequest, @RestPath String id) {
        logger.infof("Update Request for individual with id : %s", id);
    public Response update(IndividualDTO individualRequest, @RestPath String id) {
        logger.infof("PATCH Request for individual with id : %s", id);
        logger.debugf("Update Request Body : %s", individualRequest.toString());
        Individual individual = individualService.updateIndividual(id, individualRequest);
        IndividualResponse individual = individualService.updateIndividual(id, individualRequest);
        logger.infof("PATCH Request SUCCESS for individual with id : %s", id);
        return Response.ok(individual).build();
    }

    @DELETE
    @Path("/{id}")
    @Produces(MediaType.APPLICATION_JSON)
    @Consumes(MediaType.APPLICATION_JSON)
    @Operation(
            summary = "Deletes a Individual by ID",
            description = "This operation deletes a Individual entity.")
@@ -197,9 +204,9 @@ public class IndividualResource {
                            mediaType = APPLICATION_JSON,
                            schema = @Schema(implementation = ErrorMessage.class)))
    public Response delete(@RestPath String id) {
        logger.infof("Delete Request for individual with id : %s", id);
        logger.infof("DELETE Request for individual with id: %s", id);
        individualService.deleteIndividual(id);
        logger.infof("Successful Delete operation for individual with id : %s", id);
        logger.infof("DELETE Request SUCCESS for individual with id: %s", id);
        return Response.noContent().build();
    }
}
+19 −15
Original line number Diff line number Diff line
@@ -14,6 +14,8 @@ import org.etsi.osl.hypo.api.tmf.common.schema.RelatedPartyEntity;
import org.etsi.osl.hypo.api.tmf.party.api.kafka.outgoing.producer.RegistryProducer;
import org.etsi.osl.hypo.api.tmf.party.api.mapper.OrganizationMapper;
import org.etsi.osl.hypo.api.tmf.party.api.repository.IndividualRepository;
import org.etsi.osl.hypo.api.tmf.party.individual.model.IndividualDTO;
import org.etsi.osl.hypo.api.tmf.party.individual.model.IndividualResponse;
import org.etsi.osl.hypo.api.tmf.party.individual.schema.Individual;
import org.jboss.logging.Logger;

@@ -58,14 +60,16 @@ public class IndividualService {
    }

    @Transactional
    public List<Individual> getByCriteria(String fields, Map<String, String> params) {
    public List<IndividualResponse> getByCriteria(String fields, Map<String, String> params) {
        List<Individual> individuals =
                individualRepository.findWithCriteriaQuery(null, params, Collections.emptyList());
        return UtilService.getFilteredList(individuals, fields);
        return UtilService.getFilteredList(individuals, fields).stream()
                .map(organizationMapper::individualEntityToResponse)
                .toList();
    }

    @Transactional
    public Individual getByIdAndCriteria(
    public IndividualResponse getByIdAndCriteria(
            String id, String fields, Map<String, String> params, int limit) {
        List<Individual> individuals =
                individualRepository.findWithCriteriaQuery(id, params, Collections.emptyList());
@@ -75,7 +79,8 @@ public class IndividualService {
            throw new ServiceNotFoundException(notFoundMessage);
        }

        return UtilService.filterFields(individuals.get(0), fields);
        return organizationMapper.individualEntityToResponse(
                UtilService.filterFields(individuals.get(0), fields));
    }

    @Transactional
@@ -88,16 +93,16 @@ public class IndividualService {
                relatedPartyEntity -> relatedPartyService.deleteRelatedPartyById(id));
    }

    public Individual createIndividual(Individual individual, String authToken) {
        Individual persistedIndividual = createAndPersistIndividual(individual);
    @Transactional
    public IndividualResponse createIndividual(IndividualDTO individualDTO, String authToken) {
        Individual individual = organizationMapper.individualDTOtoEntity(individualDTO);
        createAndPersistIndividual(individual);

        registryProducer.sendMessageToRegistryApiForGroupPolicy(
                persistedIndividual.getFullName(), authToken);
        return persistedIndividual;
        registryProducer.sendMessageToRegistryApiForGroupPolicy(individual.getFullName(), authToken);
        return organizationMapper.individualEntityToResponse(individual);
    }

    @Transactional
    public Individual createAndPersistIndividual(Individual individual) {
    private void createAndPersistIndividual(Individual individual) {
        checkIfIdExists(individual.getId());
        if (individual.getHref() == null) {
            individual.setHref("https://serverRoot/tmf-api/party/v4/individual/");
@@ -109,17 +114,16 @@ public class IndividualService {

        RelatedPartyEntity relatedPartyEntity = organizationMapper.individualToRelatedParty(individual);
        relatedPartyService.findOrCreateRelatedPartyEntity(relatedPartyEntity);

        return individual;
    }

    @Transactional
    public Individual updateIndividual(String id, Individual newIndividual) {
    public IndividualResponse updateIndividual(String id, IndividualDTO individualDTO) {
        Individual oldIndividual = getById(id);
        Individual newIndividual = organizationMapper.individualDTOtoEntity(individualDTO);
        Individual updatedIndividual =
                organizationMapper.updateIndividual(newIndividual, oldIndividual);
        individualRepository.persist(updatedIndividual);
        return oldIndividual;
        return organizationMapper.individualEntityToResponse(oldIndividual);
    }

    private void checkIfIdExists(String id) {
+38 −25
Original line number Diff line number Diff line
@@ -18,6 +18,7 @@ import io.quarkus.test.common.http.TestHTTPEndpoint;
import io.quarkus.test.common.http.TestHTTPResource;
import io.quarkus.test.junit.QuarkusTest;
import io.quarkus.test.security.TestSecurity;
import io.restassured.common.mapper.TypeRef;
import jakarta.inject.Inject;
import jakarta.json.JsonObject;
import java.io.IOException;
@@ -33,7 +34,8 @@ import org.etsi.osl.hypo.api.tmf.common.schema.RelatedPartyEntity;
import org.etsi.osl.hypo.api.tmf.party.api.mapper.OrganizationMapper;
import org.etsi.osl.hypo.api.tmf.party.api.rest.IndividualResource;
import org.etsi.osl.hypo.api.tmf.party.api.services.IndividualService;
import org.etsi.osl.hypo.api.tmf.party.individual.schema.Individual;
import org.etsi.osl.hypo.api.tmf.party.individual.model.IndividualDTO;
import org.etsi.osl.hypo.api.tmf.party.individual.model.IndividualResponse;
import org.junit.jupiter.api.AfterEach;
import org.junit.jupiter.api.BeforeAll;
import org.junit.jupiter.api.Test;
@@ -95,9 +97,9 @@ class IndividualResourceTest {
    void shouldAddItem(JsonObject sliceJson) throws JsonProcessingException {
        final String request = sliceJson.toString();

        Individual expectedResponse = objectMapper.readValue(request, Individual.class);
        IndividualResponse expectedResponse = objectMapper.readValue(request, IndividualResponse.class);

        Individual actualResponse =
        IndividualResponse actualResponse =
                given()
                        .body(request)
                        .header(CONTENT_TYPE, JSON)
@@ -107,9 +109,12 @@ class IndividualResourceTest {
                        .then()
                        .statusCode(201)
                        .extract()
                        .as(Individual.class);
                        .as(IndividualResponse.class);

        assertThat(actualResponse).usingRecursiveComparison().isEqualTo(expectedResponse);
        assertThat(actualResponse)
                .usingRecursiveComparison()
                .ignoringFields("id", "href")
                .isEqualTo(expectedResponse);

        String organizationId = actualResponse.getId();

@@ -129,9 +134,9 @@ class IndividualResourceTest {
                        Paths.get(
                                "src/test/resources/org.etsi.osl.hypo.api.tmf.party.api/individual/expected-update-response.json"));

        Individual expectedResponse = objectMapper.readValue(inJson, Individual.class);
        IndividualResponse expectedResponse = objectMapper.readValue(inJson, IndividualResponse.class);

        Individual individual =
        IndividualResponse individual =
                given()
                        .body(request)
                        .header(CONTENT_TYPE, JSON)
@@ -141,13 +146,13 @@ class IndividualResourceTest {
                        .then()
                        .statusCode(201)
                        .extract()
                        .as(Individual.class);
                        .as(IndividualResponse.class);

        organizationMapper.updateIndividual(expectedResponse, individual);
        IndividualDTO individualDTO = organizationMapper.individualResponseToDTO(expectedResponse);

        Individual actualResponse =
        IndividualResponse actualResponse =
                given()
                        .body(individual)
                        .body(individualDTO)
                        .header(CONTENT_TYPE, JSON)
                        .header(ACCEPT, JSON)
                        .pathParam("id", individual.getId())
@@ -157,9 +162,12 @@ class IndividualResourceTest {
                        .statusCode(OK.getStatusCode())
                        .contentType(APPLICATION_JSON)
                        .extract()
                        .as(Individual.class);
                        .as(IndividualResponse.class);

        assertThat(actualResponse).usingRecursiveComparison().isEqualTo(expectedResponse);
        assertThat(actualResponse)
                .usingRecursiveComparison()
                .ignoringFields("id", "href")
                .isEqualTo(expectedResponse);
    }

    @ParameterizedTest
@@ -173,9 +181,9 @@ class IndividualResourceTest {
                        Paths.get(
                                "src/test/resources/org.etsi.osl.hypo.api.tmf.party.api/individual/expected-update-clear-response.json"));

        Individual expectedResponse = objectMapper.readValue(inJson, Individual.class);
        IndividualResponse expectedResponse = objectMapper.readValue(inJson, IndividualResponse.class);

        Individual individual =
        IndividualResponse individualResponse =
                given()
                        .body(request)
                        .header(CONTENT_TYPE, JSON)
@@ -185,7 +193,9 @@ class IndividualResourceTest {
                        .then()
                        .statusCode(201)
                        .extract()
                        .as(Individual.class);
                        .as(IndividualResponse.class);

        IndividualDTO individual = organizationMapper.individualResponseToDTO(individualResponse);

        individual.getContactMedium().clear();
        individual.getCreditRating().clear();
@@ -199,21 +209,24 @@ class IndividualResourceTest {
        individual.getIndividualIdentification().clear();
        individual.getDisability().clear();

        Individual actualResponse =
        IndividualResponse actualResponse =
                given()
                        .body(individual)
                        .header(CONTENT_TYPE, JSON)
                        .header(ACCEPT, JSON)
                        .pathParam("id", individual.getId())
                        .pathParam("id", individualResponse.getId())
                        .when()
                        .patch(individualPartyManagement + "{id}")
                        .then()
                        .statusCode(OK.getStatusCode())
                        .contentType(APPLICATION_JSON)
                        .extract()
                        .as(Individual.class);
                        .as(IndividualResponse.class);

        assertThat(actualResponse).usingRecursiveComparison().isEqualTo(expectedResponse);
        assertThat(actualResponse)
                .usingRecursiveComparison()
                .ignoringFields("id", "href")
                .isEqualTo(expectedResponse);
    }

    @ParameterizedTest
@@ -221,7 +234,7 @@ class IndividualResourceTest {
            resources = "/org.etsi.osl.hypo.api.tmf.party.api/individual/valid-add-request.json")
    void shouldGetAll(JsonObject sliceJson) {

        List<Individual> individualList =
        List<IndividualResponse> individualList =
                given()
                        .when()
                        .get(individualPartyManagement)
@@ -229,7 +242,7 @@ class IndividualResourceTest {
                        .statusCode(OK.getStatusCode())
                        .contentType(APPLICATION_JSON)
                        .extract()
                        .as(List.class);
                        .as(new TypeRef<>() {});

        assertThat(individualList).isEmpty();

@@ -254,7 +267,7 @@ class IndividualResourceTest {
                        .statusCode(OK.getStatusCode())
                        .contentType(APPLICATION_JSON)
                        .extract()
                        .as(List.class);
                        .as(new TypeRef<>() {});

        assertThat(individualList).isNotEmpty().hasSize(1);
    }
@@ -281,7 +294,7 @@ class IndividualResourceTest {
    void shouldDeleteItem(JsonObject sliceJson) {
        final String request = sliceJson.toString();

        Individual individual =
        IndividualResponse individual =
                given()
                        .body(request)
                        .header(CONTENT_TYPE, JSON)
@@ -291,7 +304,7 @@ class IndividualResourceTest {
                        .then()
                        .statusCode(201)
                        .extract()
                        .as(Individual.class);
                        .as(IndividualResponse.class);

        given()
                .pathParam("id", individual.getId())