diff --git a/src/main/java/org/gridsuite/study/server/controller/StudyController.java b/src/main/java/org/gridsuite/study/server/controller/StudyController.java index a255ceea5..c90b1631a 100644 --- a/src/main/java/org/gridsuite/study/server/controller/StudyController.java +++ b/src/main/java/org/gridsuite/study/server/controller/StudyController.java @@ -1144,30 +1144,15 @@ public ResponseEntity getSubstationDiagramAndMetadata( ResponseEntity.noContent().build(); } - @PostMapping(value = "/studies/{studyUuid}/root-networks/{rootNetworkUuid}/nodes/{nodeUuid}/network-area-diagram", consumes = MediaType.APPLICATION_JSON_VALUE, produces = MediaType.APPLICATION_JSON_VALUE) + @PostMapping(value = "/studies/{studyUuid}/root-networks/{rootNetworkUuid}/nodes/{nodeUuid}/network-area-diagram", produces = MediaType.APPLICATION_JSON_VALUE) @Operation(summary = "get the network area diagram for the given network and voltage levels") @ApiResponse(responseCode = "200", description = "The svg") public ResponseEntity getNetworkAreaDiagram( @PathVariable("studyUuid") UUID studyUuid, @PathVariable("rootNetworkUuid") UUID rootNetworkUuid, @PathVariable("nodeUuid") UUID nodeUuid, - @RequestBody List voltageLevelsIds, - @Parameter(description = "depth") @RequestParam(name = "depth", defaultValue = "0") int depth, - @Parameter(description = "Initialize NAD with Geographical Data") @RequestParam(name = "withGeoData", defaultValue = "true") boolean withGeoData) { - String result = studyService.getNetworkAreaDiagram(nodeUuid, rootNetworkUuid, voltageLevelsIds, depth, withGeoData); - return result != null ? ResponseEntity.ok().contentType(MediaType.APPLICATION_JSON).body(result) : - ResponseEntity.noContent().build(); - } - - @GetMapping(value = "/studies/{studyUuid}/root-networks/{rootNetworkUuid}/nodes/{nodeUuid}/network-area-diagram") - @Operation(summary = "get a network area diagram for the given network using a config or a filter") - @ApiResponse(responseCode = "200", description = "The svg") - public ResponseEntity getNetworkAreaDiagram( - @PathVariable("studyUuid") UUID studyUuid, - @PathVariable("rootNetworkUuid") UUID rootNetworkUuid, - @PathVariable("nodeUuid") UUID nodeUuid, - @Parameter(description = "Element parameters") @RequestParam(name = "elementParams") String elementParams) { - String result = studyService.getNetworkAreaDiagram(nodeUuid, rootNetworkUuid, elementParams); + @RequestBody String nadRequestInfos) { + String result = studyService.getNetworkAreaDiagram(nodeUuid, rootNetworkUuid, nadRequestInfos); return result != null ? ResponseEntity.ok().contentType(MediaType.APPLICATION_JSON).body(result) : ResponseEntity.noContent().build(); } diff --git a/src/main/java/org/gridsuite/study/server/service/SingleLineDiagramService.java b/src/main/java/org/gridsuite/study/server/service/SingleLineDiagramService.java index 53df1c9ea..3e8d723e1 100644 --- a/src/main/java/org/gridsuite/study/server/service/SingleLineDiagramService.java +++ b/src/main/java/org/gridsuite/study/server/service/SingleLineDiagramService.java @@ -16,8 +16,6 @@ import static org.gridsuite.study.server.StudyConstants.SINGLE_LINE_DIAGRAM_API_VERSION; import static org.gridsuite.study.server.StudyException.Type.SVG_NOT_FOUND; -import java.net.URLEncoder; -import java.nio.charset.StandardCharsets; import java.util.List; import java.util.UUID; @@ -26,8 +24,7 @@ import org.gridsuite.study.server.dto.DiagramParameters; import org.springframework.beans.factory.annotation.Value; import org.springframework.core.ParameterizedTypeReference; -import org.springframework.http.HttpMethod; -import org.springframework.http.HttpStatus; +import org.springframework.http.*; import org.springframework.stereotype.Service; import org.springframework.web.client.HttpStatusCodeException; import org.springframework.web.client.RestTemplate; @@ -170,51 +167,29 @@ public String getSubstationSvgAndMetadata(UUID networkUuid, String variantId, St return result; } - public String getNetworkAreaDiagram(UUID networkUuid, String variantId, List voltageLevelsIds, int depth, boolean withGeoData) { + public String getNetworkAreaDiagram(UUID networkUuid, String variantId, String nadRequestInfos) { var uriComponentsBuilder = UriComponentsBuilder.fromPath(DELIMITER + SINGLE_LINE_DIAGRAM_API_VERSION + - "/network-area-diagram/{networkUuid}") - .queryParam(QUERY_PARAM_DEPTH, depth) - .queryParam(QUERY_PARAM_INIT_WITH_GEO_DATA, withGeoData); + "/network-area-diagram/{networkUuid}"); if (!StringUtils.isBlank(variantId)) { uriComponentsBuilder.queryParam(QUERY_PARAM_VARIANT_ID, variantId); } var path = uriComponentsBuilder .buildAndExpand(networkUuid) .toUriString(); - String result; - try { - result = restTemplate.postForObject(singleLineDiagramServerBaseUri + path, voltageLevelsIds, String.class); - } catch (HttpStatusCodeException e) { - if (HttpStatus.NOT_FOUND.equals(e.getStatusCode())) { - throw new StudyException(SVG_NOT_FOUND, VOLTAGE_LEVEL + voltageLevelsIds + NOT_FOUND); - } else { - throw e; - } - } - return result; - } - public String getNetworkAreaDiagram(UUID networkUuid, String variantId, String elementParams) { - var uriComponentsBuilder = UriComponentsBuilder.fromPath(DELIMITER + SINGLE_LINE_DIAGRAM_API_VERSION + - "/network-area-diagram/{networkUuid}") - .queryParam(QUERY_PARAM_ELEMENT_PARAMS, URLEncoder.encode(elementParams, StandardCharsets.UTF_8)); - if (!StringUtils.isBlank(variantId)) { - uriComponentsBuilder.queryParam(QUERY_PARAM_VARIANT_ID, variantId); - } - var path = uriComponentsBuilder - .buildAndExpand(networkUuid) - .toUriString(); - String result; + var headers = new HttpHeaders(); + headers.setContentType(MediaType.APPLICATION_JSON); + HttpEntity request = new HttpEntity<>(nadRequestInfos, headers); + try { - result = restTemplate.getForObject(singleLineDiagramServerBaseUri + path, String.class); + return restTemplate.postForObject(singleLineDiagramServerBaseUri + path, request, String.class); } catch (HttpStatusCodeException e) { if (HttpStatus.NOT_FOUND.equals(e.getStatusCode())) { - throw new StudyException(SVG_NOT_FOUND, ELEMENT + NOT_FOUND); + throw new StudyException(SVG_NOT_FOUND, VOLTAGE_LEVEL + NOT_FOUND); } else { throw e; } } - return result; } public void setSingleLineDiagramServerBaseUri(String singleLineDiagramServerBaseUri) { diff --git a/src/main/java/org/gridsuite/study/server/service/StudyService.java b/src/main/java/org/gridsuite/study/server/service/StudyService.java index 998cbbd92..57671dfde 100644 --- a/src/main/java/org/gridsuite/study/server/service/StudyService.java +++ b/src/main/java/org/gridsuite/study/server/service/StudyService.java @@ -1301,27 +1301,14 @@ public String getSubstationSvgAndMetadata(String substationId, DiagramParameters } } - public String getNetworkAreaDiagram(UUID nodeUuid, UUID rootNetworkUuid, List voltageLevelsIds, int depth, boolean withGeoData) { + public String getNetworkAreaDiagram(UUID nodeUuid, UUID rootNetworkUuid, String nadRequestInfos) { UUID networkUuid = rootNetworkService.getNetworkUuid(rootNetworkUuid); if (networkUuid == null) { throw new StudyException(ROOT_NETWORK_NOT_FOUND); } String variantId = networkModificationTreeService.getVariantId(nodeUuid, rootNetworkUuid); if (networkStoreService.existVariant(networkUuid, variantId)) { - return singleLineDiagramService.getNetworkAreaDiagram(networkUuid, variantId, voltageLevelsIds, depth, withGeoData); - } else { - return null; - } - } - - public String getNetworkAreaDiagram(UUID nodeUuid, UUID rootNetworkUuid, String elementParams) { - UUID networkUuid = rootNetworkService.getNetworkUuid(rootNetworkUuid); - if (networkUuid == null) { - throw new StudyException(ROOT_NETWORK_NOT_FOUND); - } - String variantId = networkModificationTreeService.getVariantId(nodeUuid, rootNetworkUuid); - if (networkStoreService.existVariant(networkUuid, variantId)) { - return singleLineDiagramService.getNetworkAreaDiagram(networkUuid, variantId, elementParams); + return singleLineDiagramService.getNetworkAreaDiagram(networkUuid, variantId, nadRequestInfos); } else { return null; } diff --git a/src/test/java/org/gridsuite/study/server/NetworkAreaDiagramTest.java b/src/test/java/org/gridsuite/study/server/NetworkAreaDiagramTest.java index ea91be653..83f85dc3b 100644 --- a/src/test/java/org/gridsuite/study/server/NetworkAreaDiagramTest.java +++ b/src/test/java/org/gridsuite/study/server/NetworkAreaDiagramTest.java @@ -18,16 +18,18 @@ import org.springframework.http.HttpHeaders; import org.springframework.http.MediaType; import org.springframework.test.web.servlet.MockMvc; +import org.testcontainers.shaded.com.fasterxml.jackson.core.JsonProcessingException; +import org.testcontainers.shaded.com.fasterxml.jackson.databind.ObjectMapper; -import java.net.URLEncoder; +import java.util.HashMap; import java.util.List; import java.util.Map; import java.util.UUID; -import java.nio.charset.StandardCharsets; +import static com.github.tomakehurst.wiremock.client.WireMock.equalTo; import static com.github.tomakehurst.wiremock.core.WireMockConfiguration.wireMockConfig; import static org.mockito.Mockito.when; -import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.get; +import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.post; import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.content; import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status; @@ -60,7 +62,6 @@ class NetworkAreaDiagramTest { private static final UUID ELEMENT_UUID = UUID.randomUUID(); private static final UUID ROOTNETWORK_UUID = UUID.randomUUID(); private static final UUID NODE_UUID = UUID.randomUUID(); - private static final String ELEMENT_PARAMETERS = "{\"elementType\":\"DIAGRAM_CONFIG\",\"elementUuid\":\"" + ELEMENT_UUID + "\"}"; @BeforeEach void setUp() { @@ -74,59 +75,84 @@ void setUp() { when(networkStoreService.getVariantsInfos(NETWORK_UUID)).thenReturn(List.of(new VariantInfos(VariantManagerConstants.INITIAL_VARIANT_ID, 0))); } + private String createNadRequestInfos( + UUID nadConfigUuid, + UUID filterUuid, + List voltageLevelIds, + List voltageLevelToExpandIds, + List voltageLevelToOmitIds, + boolean withGeoData + ) throws JsonProcessingException { + Map requestBody = new HashMap<>(); + requestBody.put("nadConfigUuid", nadConfigUuid); + requestBody.put("filterUuid", filterUuid); + requestBody.put("voltageLevelIds", voltageLevelIds); + requestBody.put("voltageLevelToExpandIds", voltageLevelToExpandIds); + requestBody.put("voltageLevelToOmitIds", voltageLevelToOmitIds); + requestBody.put("positions", List.of()); + requestBody.put("withGeoData", withGeoData); + + ObjectMapper objectMapper = new ObjectMapper(); + return objectMapper.writeValueAsString(requestBody); + } + @Test void testGetNetworkAreaDiagramFromConfig() throws Exception { - UUID stubId = wireMockServer.stubFor(WireMock.get(WireMock.urlPathMatching(SINGLE_LINE_DIAGRAM_SERVER_BASE_URL + ".*")) + String nadRequestConfigInfos = createNadRequestInfos(ELEMENT_UUID, null, List.of(), List.of(), List.of(), true); + UUID stubId = wireMockServer.stubFor(WireMock.post(WireMock.urlPathMatching(SINGLE_LINE_DIAGRAM_SERVER_BASE_URL + ".*")) + .withRequestBody(equalTo(nadRequestConfigInfos)) .willReturn(WireMock.ok() .withHeader(HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON_VALUE) .withBody("nad-svg-from-config") )).getId(); - mockMvc.perform(get("/v1/studies/{studyUuid}/root-networks/{rootNetworkUuid}/nodes/{nodeUuid}/network-area-diagram", + mockMvc.perform(post("/v1/studies/{studyUuid}/root-networks/{rootNetworkUuid}/nodes/{nodeUuid}/network-area-diagram", NETWORK_UUID, ROOTNETWORK_UUID, NODE_UUID) - .param("elementParams", ELEMENT_PARAMETERS) + .content(nadRequestConfigInfos).contentType(MediaType.APPLICATION_JSON) .header("userId", USER1)) .andExpectAll(status().isOk(), content().string("nad-svg-from-config")) .andReturn(); - - wireMockUtils.verifyGetRequest(stubId, SINGLE_LINE_DIAGRAM_SERVER_BASE_URL + NETWORK_UUID, Map.of( - "elementParams", WireMock.equalTo(URLEncoder.encode(ELEMENT_PARAMETERS, StandardCharsets.UTF_8)), - "variantId", WireMock.equalTo(VariantManagerConstants.INITIAL_VARIANT_ID))); + wireMockUtils.verifyPostRequest(stubId, SINGLE_LINE_DIAGRAM_SERVER_BASE_URL + NETWORK_UUID, false, Map.of("variantId", WireMock.equalTo(VariantManagerConstants.INITIAL_VARIANT_ID)), nadRequestConfigInfos); } @Test void testGetNetworkAreaDiagramFromConfigVariantError() throws Exception { - when(networkModificationTreeService.getVariantId(NODE_UUID, ROOTNETWORK_UUID)).thenReturn("Another_variant"); + String nadRequestConfigInfos = createNadRequestInfos(ELEMENT_UUID, null, List.of(), List.of(), List.of(), true); - mockMvc.perform(get("/v1/studies/{studyUuid}/root-networks/{rootNetworkUuid}/nodes/{nodeUuid}/network-area-diagram", + when(networkModificationTreeService.getVariantId(NODE_UUID, ROOTNETWORK_UUID)).thenReturn("Another_variant"); + mockMvc.perform(post("/v1/studies/{studyUuid}/root-networks/{rootNetworkUuid}/nodes/{nodeUuid}/network-area-diagram", NETWORK_UUID, ROOTNETWORK_UUID, NODE_UUID) - .param("elementParams", ELEMENT_PARAMETERS) + .content(nadRequestConfigInfos).contentType(MediaType.APPLICATION_JSON) .header("userId", USER1)) .andExpectAll(status().isNoContent()); } @Test void testGetNetworkAreaDiagramFromConfigRootNetworkError() throws Exception { - mockMvc.perform(get("/v1/studies/{studyUuid}/root-networks/{rootNetworkUuid}/nodes/{nodeUuid}/network-area-diagram", + String nadRequestConfigInfos = createNadRequestInfos(ELEMENT_UUID, null, List.of(), List.of(), List.of(), true); + + mockMvc.perform(post("/v1/studies/{studyUuid}/root-networks/{rootNetworkUuid}/nodes/{nodeUuid}/network-area-diagram", UUID.randomUUID(), UUID.randomUUID(), UUID.randomUUID()) - .param("elementParams", ELEMENT_PARAMETERS) + .content(nadRequestConfigInfos).contentType(MediaType.APPLICATION_JSON) .header("userId", USER1)) .andExpectAll(status().isNotFound()); } @Test void testGetNetworkAreaDiagramFromConfigElementUuidNotFound() throws Exception { - UUID stubId = wireMockServer.stubFor(WireMock.get(WireMock.urlPathMatching(SINGLE_LINE_DIAGRAM_SERVER_BASE_URL + ".*")) + String nadRequestConfigInfos = createNadRequestInfos(ELEMENT_UUID, null, List.of(), List.of(), List.of(), true); + + UUID stubId = wireMockServer.stubFor(WireMock.post(WireMock.urlPathMatching(SINGLE_LINE_DIAGRAM_SERVER_BASE_URL + ".*")) + .withRequestBody(equalTo(nadRequestConfigInfos)) .willReturn(WireMock.notFound())).getId(); - mockMvc.perform(get("/v1/studies/{studyUuid}/root-networks/{rootNetworkUuid}/nodes/{nodeUuid}/network-area-diagram", + mockMvc.perform(post("/v1/studies/{studyUuid}/root-networks/{rootNetworkUuid}/nodes/{nodeUuid}/network-area-diagram", NETWORK_UUID, ROOTNETWORK_UUID, NODE_UUID) - .param("elementParams", ELEMENT_PARAMETERS) + .content(nadRequestConfigInfos).contentType(MediaType.APPLICATION_JSON) .header("userId", USER1)) .andExpectAll(status().isNotFound()); - wireMockUtils.verifyGetRequest(stubId, SINGLE_LINE_DIAGRAM_SERVER_BASE_URL + NETWORK_UUID, Map.of( - "elementParams", WireMock.equalTo(URLEncoder.encode(ELEMENT_PARAMETERS, StandardCharsets.UTF_8)), - "variantId", WireMock.equalTo(VariantManagerConstants.INITIAL_VARIANT_ID))); + wireMockUtils.verifyPostRequest(stubId, SINGLE_LINE_DIAGRAM_SERVER_BASE_URL + NETWORK_UUID, Map.of( + "variantId", WireMock.equalTo(VariantManagerConstants.INITIAL_VARIANT_ID))); } } diff --git a/src/test/java/org/gridsuite/study/server/SingleLineDiagramTest.java b/src/test/java/org/gridsuite/study/server/SingleLineDiagramTest.java index 5dde242ce..8777c48ad 100644 --- a/src/test/java/org/gridsuite/study/server/SingleLineDiagramTest.java +++ b/src/test/java/org/gridsuite/study/server/SingleLineDiagramTest.java @@ -57,6 +57,7 @@ import org.springframework.test.web.servlet.MockMvc; import org.springframework.test.web.servlet.MvcResult; import org.springframework.test.web.servlet.request.MockHttpServletRequestBuilder; +import org.testcontainers.shaded.com.fasterxml.jackson.core.JsonProcessingException; import java.util.*; import java.util.stream.Collectors; @@ -218,7 +219,7 @@ public MockResponse dispatch(RecordedRequest request) { case "/v1/substation-svg/" + NETWORK_UUID_STRING + "/substationErrorId?useName=false¢erLabel=false&diagonalLabel=false&topologicalColoring=false&substationLayout=horizontal&language=en": case "/v1/substation-svg-and-metadata/" + NETWORK_UUID_STRING + "/substationErrorId?useName=false¢erLabel=false&diagonalLabel=false&topologicalColoring=false&substationLayout=horizontal&language=en": return new MockResponse(500, Headers.of(HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON_VALUE), "{\"timestamp\":\"2020-12-14T10:27:11.760+0000\",\"status\":500,\"error\":\"Internal Server Error\",\"message\":\"tmp\",\"path\":\"/v1/networks\"}"); - case "/v1/network-area-diagram/" + NETWORK_UUID_STRING + "?depth=0&withGeoData=true": + case "/v1/network-area-diagram/" + NETWORK_UUID_STRING : return new MockResponse(200, Headers.of(HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON_VALUE), "nad-svg"); case "/v1/svg-component-libraries": @@ -239,6 +240,22 @@ public MockResponse dispatch(RecordedRequest request) { server.setDispatcher(dispatcher); } + private String createNadRequestInfos( + List voltageLevelIds + ) throws JsonProcessingException { + Map requestBody = new HashMap<>(); + requestBody.put("nadConfigUuid", null); + requestBody.put("filterUuid", null); + requestBody.put("voltageLevelIds", voltageLevelIds); + requestBody.put("voltageLevelToExpandIds", List.of()); + requestBody.put("voltageLevelToOmitIds", List.of()); + requestBody.put("positions", List.of()); + requestBody.put("withGeoData", true); + + org.testcontainers.shaded.com.fasterxml.jackson.databind.ObjectMapper mapper = new org.testcontainers.shaded.com.fasterxml.jackson.databind.ObjectMapper(); + return mapper.writeValueAsString(requestBody); + } + @Test void testDiagramsAndGraphics(final MockWebServer server) throws Exception { MvcResult mvcResult; @@ -347,22 +364,21 @@ void testDiagramsAndGraphics(final MockWebServer server) throws Exception { randomUuid, randomUuid, rootNodeUuid, "substationId")).andExpect(status().isNotFound()); // get the network area diagram - mockMvc.perform(post("/v1/studies/{studyUuid}/root-networks/{rootNetworkUuid}/nodes/{nodeUuid}/network-area-diagram?&depth=0&withGeoData=true", studyNameUserIdUuid, firstRootNetworkUuid, rootNodeUuid) - .content("[\"vlFr1A\"]") - .contentType(MediaType.APPLICATION_JSON)) + String nadRequestConfigInfos = createNadRequestInfos(List.of("vlFr1A")); + mockMvc.perform(post("/v1/studies/{studyUuid}/root-networks/{rootNetworkUuid}/nodes/{nodeUuid}/network-area-diagram", studyNameUserIdUuid, firstRootNetworkUuid, rootNodeUuid) + .content(nadRequestConfigInfos).contentType(MediaType.APPLICATION_JSON)) .andExpectAll( content().contentType(MediaType.APPLICATION_JSON), status().isOk(), content().string("nad-svg") ); - assertTrue(TestUtils.getRequestsDone(1, server).contains(String.format("/v1/network-area-diagram/" + NETWORK_UUID_STRING + "?depth=0&withGeoData=true"))); + assertTrue(TestUtils.getRequestsDone(1, server).contains(String.format("/v1/network-area-diagram/" + NETWORK_UUID_STRING))); // get the network area diagram from a study that doesn't exist - mockMvc.perform(post("/v1/studies/{studyUuid}/root-networks/{rootNetworkUuid}/nodes/{nodeUuid}/network-area-diagram?&depth=0&withGeoData=true", randomUuid, randomUuid, rootNodeUuid) - .content("[\"vlFr1A\"]") - .contentType(MediaType.APPLICATION_JSON)) - .andExpect(status().isNotFound()); + mockMvc.perform(post("/v1/studies/{studyUuid}/root-networks/{rootNetworkUuid}/nodes/{nodeUuid}/network-area-diagram", randomUuid, randomUuid, rootNodeUuid) + .content(nadRequestConfigInfos).contentType(MediaType.APPLICATION_JSON)) + .andExpect(status().isNotFound()); //get voltage levels mvcResult = getNetworkElementsInfos(studyNameUserIdUuid, firstRootNetworkUuid, rootNodeUuid, "MAP", "VOLTAGE_LEVEL", null, objectMapper.writeValueAsString(List.of()), TestUtils.resourceToString("/network-voltage-levels-infos.json")); @@ -521,10 +537,11 @@ void testDiagramsVariantError() throws Exception { status().isNoContent()); //get the network area diagram on a non existing variant - mockMvc.perform(post("/v1/studies/{studyUuid}/root-networks/{rootNetworkUuid}/nodes/{nodeUuid}/network-area-diagram?depth=0", + String nadRequestConfigInfos = createNadRequestInfos(List.of("vlFr1A")); + mockMvc.perform(post("/v1/studies/{studyUuid}/root-networks/{rootNetworkUuid}/nodes/{nodeUuid}/network-area-diagram", studyNameUserIdUuid, firstRootNetworkUuid, modificationNodeUuid) - .content("[\"vlFr1A\"]") - .contentType(MediaType.APPLICATION_JSON)).andExpectAll( + .content(nadRequestConfigInfos).contentType(MediaType.APPLICATION_JSON)) + .andExpectAll( status().isNoContent()); }