<groupId>org.apache.httpcomponents.core5</groupId>
<artifactId>httpcore5</artifactId>
</dependency>
- <dependency>
- <groupId>org.glassfish.jersey.inject</groupId>
- <artifactId>jersey-hk2</artifactId>
- <version>${version.jersey}</version>
- </dependency>
</dependencies>
<build>
<name>${project.artifactId}</name>
<description>HTTP participant, that performs CRUD operations on Microservices through REST</description>
- <dependencies>
- <dependency>
- <groupId>org.glassfish.jersey.inject</groupId>
- <artifactId>jersey-hk2</artifactId>
- <version>${version.jersey}</version>
- </dependency>
- </dependencies>
-
<build>
<plugins>
<plugin>
<groupId>org.apache.httpcomponents.core5</groupId>
<artifactId>httpcore5</artifactId>
</dependency>
- <dependency>
- <groupId>org.glassfish.jersey.inject</groupId>
- <artifactId>jersey-hk2</artifactId>
- <version>${version.jersey}</version>
- </dependency>
</dependencies>
<build>
/*-
* ============LICENSE_START=======================================================
- * Copyright (C) 2021, 2023-2024 Nordix Foundation.
+ * Copyright (C) 2021, 2023-2025 OpenInfra Foundation Europe. All rights reserved.
* ================================================================================
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
package org.onap.policy.clamp.acm.participant.policy.client;
-import jakarta.ws.rs.client.Entity;
-import jakarta.ws.rs.core.HttpHeaders;
-import jakarta.ws.rs.core.MediaType;
-import jakarta.ws.rs.core.Response;
-import jakarta.ws.rs.core.Response.Status;
-import java.io.IOException;
-import java.util.Collections;
-import java.util.Map;
-import org.onap.policy.clamp.common.acm.exception.AutomationCompositionRuntimeException;
-import org.onap.policy.common.endpoints.http.client.HttpClient;
-import org.onap.policy.common.endpoints.http.client.HttpClientFactoryInstance;
-import org.onap.policy.common.parameters.topic.BusTopicParams;
+import java.util.List;
+import lombok.RequiredArgsConstructor;
+import org.apache.commons.lang3.StringUtils;
+import org.onap.policy.clamp.acm.participant.policy.main.parameters.RestClientParameters;
+import org.onap.policy.common.utils.coder.Coder;
+import org.onap.policy.common.utils.coder.CoderException;
+import org.onap.policy.common.utils.coder.StandardCoder;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
+import org.springframework.http.HttpHeaders;
+import org.springframework.http.HttpStatus;
+import org.springframework.http.MediaType;
+import org.springframework.web.reactive.function.BodyInserters;
+import org.springframework.web.reactive.function.client.ClientResponse;
+import org.springframework.web.reactive.function.client.WebClient;
+import org.springframework.web.reactive.function.client.WebClientResponseException;
+import reactor.core.publisher.Mono;
-public abstract class AbstractHttpClient implements AutoCloseable {
+@RequiredArgsConstructor
+public abstract class AbstractHttpClient {
private static final Logger LOGGER = LoggerFactory.getLogger(AbstractHttpClient.class);
- private final HttpClient httpclient;
+ private static final Coder CODER = new StandardCoder();
+ private final RestClientParameters parameters;
- /**
- * Constructor.
- *
- * @param policyParticipantParameters the parameters for the policy participant
- * @throws AutomationCompositionRuntimeException on client start errors
- */
- protected AbstractHttpClient(BusTopicParams policyParticipantParameters) {
+ protected String executePost(String path, final Object entity) {
+ var webClient = WebClient.builder().baseUrl(this.getBaseUrl())
+ .defaultHeaders(this::headersConsumer).build();
+ return webClient.post()
+ .uri(path)
+ .body(BodyInserters.fromValue(encode(entity)))
+ .exchangeToMono(this::responseHandler).block();
+ }
+
+ private String encode(Object entity) {
try {
- httpclient = HttpClientFactoryInstance.getClientFactory().build(policyParticipantParameters);
- } catch (final Exception e) {
- throw new AutomationCompositionRuntimeException(Status.INTERNAL_SERVER_ERROR, " Client failed to start", e);
+ return CODER.encode(entity);
+ } catch (CoderException e) {
+ throw new WebClientResponseException(HttpStatus.BAD_REQUEST.value(), e.getMessage(), null, null, null);
+ }
+ }
+
+ private String getBaseUrl() {
+ return "http://" + parameters.getHostname() + ":" + parameters.getPort();
+ }
+
+ private Mono<String> responseHandler(ClientResponse clientResponse) {
+ if (clientResponse.statusCode().is2xxSuccessful()) {
+ return clientResponse.bodyToMono(String.class);
+ } else {
+ LOGGER.error("Invocation Post failed Response status: {}", clientResponse.statusCode());
+ return clientResponse.createException().flatMap(Mono::error);
}
}
- protected Response executePost(String path, final Entity<?> entity) {
- var response = httpclient.post(path, entity, Map.of(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON,
- HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON));
- if (response.getStatus() / 100 != 2) {
- LOGGER.error("Invocation of path {} failed for entity {}. Response status: {}, Response status info: {}",
- path, entity, response.getStatus(), response.getStatusInfo());
+ private void headersConsumer(HttpHeaders headers) {
+ headers.setAccept(List.of(MediaType.APPLICATION_JSON));
+ headers.setContentType(MediaType.APPLICATION_JSON);
+ if (StringUtils.isNotBlank(parameters.getUserName())
+ && StringUtils.isNotBlank(parameters.getPassword())) {
+ headers.setBasicAuth(parameters.getUserName(), parameters.getPassword());
}
- return response;
}
- protected Response executeDelete(String path) {
- return httpclient.delete(path, Collections.emptyMap());
+ protected void executeDelete(String path) {
+ var webClient = WebClient.builder().baseUrl(this.getBaseUrl())
+ .defaultHeaders(this::headersConsumer).build();
+ webClient.delete()
+ .uri(path)
+ .exchangeToMono(this::responseDeleteHandler).block();
}
- @Override
- public void close() throws IOException {
- httpclient.shutdown();
+ private Mono<Void> responseDeleteHandler(ClientResponse clientResponse) {
+ if (clientResponse.statusCode().is2xxSuccessful()) {
+ return clientResponse.releaseBody();
+ } else {
+ LOGGER.error("Invocation Delete failed Response status: {}", clientResponse.statusCode());
+ return clientResponse.createException().flatMap(Mono::error);
+ }
}
}
/*-
* ============LICENSE_START=======================================================
- * Copyright (C) 2021,2023 Nordix Foundation.
+ * Copyright (C) 2021,2023,2025 OpenInfra Foundation Europe. All rights reserved.
* ================================================================================
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
package org.onap.policy.clamp.acm.participant.policy.client;
-import jakarta.ws.rs.client.Entity;
-import jakarta.ws.rs.core.MediaType;
-import jakarta.ws.rs.core.Response;
import org.onap.policy.clamp.acm.participant.policy.main.parameters.ParticipantPolicyParameters;
import org.onap.policy.models.tosca.authorative.concepts.ToscaServiceTemplate;
import org.springframework.stereotype.Component;
* @param toscaServiceTemplate the whole ToscaServiceTemplate
* @return Response
*/
- public Response createPolicyType(ToscaServiceTemplate toscaServiceTemplate) {
- return executePost(POLICY_URI + "policytypes", Entity.entity(toscaServiceTemplate, MediaType.APPLICATION_JSON));
+ public String createPolicyType(ToscaServiceTemplate toscaServiceTemplate) {
+ return executePost(POLICY_URI + "policytypes", toscaServiceTemplate);
}
/**
* @param toscaServiceTemplate the whole ToscaServiceTemplate
* @return Response
*/
- public Response createPolicy(final ToscaServiceTemplate toscaServiceTemplate) {
- return executePost(POLICY_URI + "policies", Entity.entity(toscaServiceTemplate, MediaType.APPLICATION_JSON));
+ public String createPolicy(final ToscaServiceTemplate toscaServiceTemplate) {
+ return executePost(POLICY_URI + "policies", toscaServiceTemplate);
}
/**
*
* @param policyName the name of the policy to be deleted
* @param policyVersion the version of the policy to be deleted
- * @return Response
*/
- public Response deletePolicy(final String policyName, final String policyVersion) {
- return executeDelete(POLICY_URI + "policies/" + policyName + "/versions/" + policyVersion);
+ public void deletePolicy(final String policyName, final String policyVersion) {
+ executeDelete(POLICY_URI + "policies/" + policyName + "/versions/" + policyVersion);
}
/**
*
* @param policyTypeName the name of the policy to be deleted
* @param policyTypeVersion the version of the policy to be deleted
- * @return Response
*/
- public Response deletePolicyType(final String policyTypeName, final String policyTypeVersion) {
- return executeDelete(POLICY_URI + "policytypes/" + policyTypeName + "/versions/" + policyTypeVersion);
+ public void deletePolicyType(final String policyTypeName, final String policyTypeVersion) {
+ executeDelete(POLICY_URI + "policytypes/" + policyTypeName + "/versions/" + policyTypeVersion);
}
}
package org.onap.policy.clamp.acm.participant.policy.client;
-import jakarta.ws.rs.client.Entity;
-import jakarta.ws.rs.core.MediaType;
-import jakarta.ws.rs.core.Response;
import java.util.List;
import org.onap.policy.clamp.acm.participant.policy.concepts.DeploymentGroup;
import org.onap.policy.clamp.acm.participant.policy.concepts.DeploymentGroups;
* @param action the action to deploy/undeploy policy
* @return Response
*/
- public Response handlePolicyDeployOrUndeploy(final String policyName, final String policyVersion,
+ public String handlePolicyDeployOrUndeploy(final String policyName, final String policyVersion,
final DeploymentSubGroup.Action action) {
var policies = List.of(new ToscaConceptIdentifier(policyName, policyVersion));
var groups = new DeploymentGroups();
groups.setGroups(List.of(group));
- return executePost(PAP_URI + "pdps/deployments/batch", Entity.entity(groups, MediaType.APPLICATION_JSON));
+ return executePost(PAP_URI + "pdps/deployments/batch", groups);
}
}
import java.util.List;
import java.util.Map;
import java.util.UUID;
-import org.apache.hc.core5.http.HttpStatus;
import org.onap.policy.clamp.acm.participant.intermediary.api.CompositionElementDto;
import org.onap.policy.clamp.acm.participant.intermediary.api.InstanceElementDto;
import org.onap.policy.clamp.acm.participant.intermediary.api.ParticipantIntermediaryApi;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Component;
+import org.springframework.web.reactive.function.client.WebClientResponseException;
/**
* This class handles implementation of automationCompositionElement updates.
// Deploy all policies of this automationComposition from Policy Framework
if (!policyList.isEmpty()) {
for (var policy : policyList) {
- var deployPolicyResp = papHttpClient.handlePolicyDeployOrUndeploy(policy.getName(), policy.getVersion(),
- DeploymentSubGroup.Action.POST).getStatus();
- if (deployPolicyResp != HttpStatus.SC_ACCEPTED) {
+ try {
+ papHttpClient.handlePolicyDeployOrUndeploy(policy.getName(), policy.getVersion(),
+ DeploymentSubGroup.Action.POST);
+ } catch (WebClientResponseException e) {
+ LOGGER.error(e.getMessage(), e);
deployFailure = true;
}
}
@Override
public void deploy(CompositionElementDto compositionElement, InstanceElementDto instanceElement)
throws PfModelException {
- var createPolicyTypeResp = HttpStatus.SC_OK;
- var createPolicyResp = HttpStatus.SC_OK;
+ var createPolicyTypeResp = true;
+ var createPolicyResp = true;
var automationCompositionDefinition = getToscaServiceTemplate(instanceElement.inProperties());
if (automationCompositionDefinition.getToscaTopologyTemplate() == null) {
if (automationCompositionDefinition.getPolicyTypes() != null) {
LOGGER.info("Found Policy Types in automation composition definition: {} , Creating Policy Types",
automationCompositionDefinition.getName());
- try (var response = apiHttpClient.createPolicyType(automationCompositionDefinition)) {
- createPolicyTypeResp = response.getStatus();
+ try {
+ apiHttpClient.createPolicyType(automationCompositionDefinition);
+ } catch (WebClientResponseException e) {
+ LOGGER.error(e.getMessage(), e);
+ createPolicyTypeResp = false;
}
}
if (automationCompositionDefinition.getToscaTopologyTemplate().getPolicies() != null) {
LOGGER.info("Found Policies in automation composition definition: {} , Creating Policies",
automationCompositionDefinition.getName());
- try (var response = apiHttpClient.createPolicy(automationCompositionDefinition)) {
- createPolicyResp = response.getStatus();
+ try {
+ apiHttpClient.createPolicy(automationCompositionDefinition);
+ } catch (WebClientResponseException e) {
+ LOGGER.error(e.getMessage(), e);
+ createPolicyResp = false;
}
}
- if (isSuccess(createPolicyTypeResp) && isSuccess(createPolicyResp)) {
+ if (createPolicyTypeResp && createPolicyResp) {
LOGGER.info(
"PolicyTypes/Policies for the automation composition element : {} are created " + "successfully",
instanceElement.elementId());
}
}
- private boolean isSuccess(int status) {
- return status == HttpStatus.SC_OK || status == HttpStatus.SC_CREATED;
- }
-
private List<ToscaConceptIdentifier> getPolicyTypeList(ToscaServiceTemplate serviceTemplate) {
List<ToscaConceptIdentifier> policyTypeList = new ArrayList<>();
if (serviceTemplate.getPolicyTypes() != null) {
/*-
* ============LICENSE_START=======================================================
- * Copyright (C) 2021, 2024 Nordix Foundation.
+ * Copyright (C) 2021,2024-2025 OpenInfra Foundation Europe. All rights reserved.
* ================================================================================
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
import lombok.Setter;
import org.onap.policy.clamp.acm.participant.intermediary.parameters.ParticipantIntermediaryParameters;
import org.onap.policy.clamp.acm.participant.intermediary.parameters.ParticipantParameters;
-import org.onap.policy.common.parameters.rest.RestClientParameters;
-import org.onap.policy.common.parameters.validation.ParameterGroupConstraint;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.validation.annotation.Validated;
private ParticipantIntermediaryParameters intermediaryParameters;
@NotNull
- @ParameterGroupConstraint
+ @Valid
private RestClientParameters policyApiParameters;
@NotNull
- @ParameterGroupConstraint
+ @Valid
private RestClientParameters policyPapParameters;
@NotBlank
--- /dev/null
+/*-
+ * ============LICENSE_START=======================================================
+ * Copyright (C) 2025 OpenInfra Foundation Europe. All rights reserved.
+ * ================================================================================
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ * SPDX-License-Identifier: Apache-2.0
+ * ============LICENSE_END=========================================================
+ */
+
+package org.onap.policy.clamp.acm.participant.policy.main.parameters;
+
+import jakarta.validation.constraints.Max;
+import jakarta.validation.constraints.Min;
+import jakarta.validation.constraints.NotBlank;
+import lombok.Getter;
+import lombok.Setter;
+import org.springframework.validation.annotation.Validated;
+
+@Validated
+@Getter
+@Setter
+public class RestClientParameters {
+ @NotBlank
+ private String clientName;
+
+ @Min(0)
+ @Max(65535)
+ private int port;
+
+ private String userName;
+ private String password;
+
+ @NotBlank
+ private String hostname;
+}
package org.onap.policy.clamp.acm.participant.policy.client;
-import static org.assertj.core.api.Assertions.assertThat;
import static org.junit.jupiter.api.Assertions.assertDoesNotThrow;
import static org.junit.jupiter.api.Assertions.assertThrows;
-import jakarta.ws.rs.client.Entity;
-import jakarta.ws.rs.core.MediaType;
-import jakarta.ws.rs.core.Response;
import java.io.IOException;
import okhttp3.mockwebserver.Dispatcher;
import okhttp3.mockwebserver.MockResponse;
import org.junit.jupiter.api.BeforeAll;
import org.junit.jupiter.api.Test;
import org.onap.policy.clamp.acm.participant.policy.concepts.DeploymentSubGroup;
+import org.onap.policy.clamp.acm.participant.policy.main.parameters.CommonTestData;
import org.onap.policy.clamp.acm.participant.policy.main.parameters.ParticipantPolicyParameters;
-import org.onap.policy.clamp.common.acm.exception.AutomationCompositionRuntimeException;
-import org.onap.policy.common.parameters.rest.RestClientParameters;
+import org.onap.policy.clamp.acm.participant.policy.main.parameters.RestClientParameters;
import org.onap.policy.models.tosca.authorative.concepts.ToscaServiceTemplate;
+import org.springframework.web.reactive.function.client.WebClientException;
/**
* Tests for api and pap http clients.
private static PolicyPapHttpClient papHttpClient;
+ private static ToscaServiceTemplate serviceTemplate;
+
/**
* Set up Mock server.
*/
@BeforeAll
static void setUpMockServer() throws IOException {
+ serviceTemplate = CommonTestData
+ .getToscaServiceTemplate("clamp/acm/pmsh/funtional-pmsh-usecase-migration.yaml");
// Setup mock web server
int mockServerPort = 42545;
- MockWebServer mockServer = new MockWebServer();
+ var mockServer = new MockWebServer();
mockServer.start(mockServerPort);
mockServer.setDispatcher(new Dispatcher() {
@NotNull
.setResponseCode(200)
.addHeader("Content-Type", "application/json");
}
+ if (path.equals("/policy/api/v1/policies") && "POST".equals(request.getMethod())
+ && request.getBody().size() < 40) {
+ return new MockResponse().setResponseCode(404);
+ }
if (path.equals("/policy/api/v1/policies") && "POST".equals(request.getMethod())) {
return new MockResponse()
.setResponseCode(200)
&& "DELETE".equals(request.getMethod())) {
return new MockResponse().setResponseCode(200);
}
+ if (path.matches("^/policy/api/v1/policies/wrongPolicy/versions/[^/]+$")
+ && "DELETE".equals(request.getMethod())) {
+ return new MockResponse().setResponseCode(404);
+ }
if (path.matches("^/policy/api/v1/policies/[^/]+/versions/[^/]+$")
&& "DELETE".equals(request.getMethod())) {
return new MockResponse().setResponseCode(200);
});
// Setup mock api and pap client
- ParticipantPolicyParameters params = new ParticipantPolicyParameters();
- RestClientParameters restClientParameters = getMockClientParameters(mockServerPort);
+ var params = new ParticipantPolicyParameters();
+ var restClientParameters = getMockClientParameters(mockServerPort);
params.setPolicyApiParameters(restClientParameters);
params.setPolicyPapParameters(restClientParameters);
papHttpClient = new PolicyPapHttpClient(params);
}
-
@Test
void testCreatePolicy() {
- assertDoesNotThrow(() -> apiHttpClient.createPolicy(getTestToscaServiceTemplate()));
+ assertDoesNotThrow(() -> apiHttpClient.createPolicy(serviceTemplate));
+ }
+
+ @Test
+ void testCreateBabPolicy() {
+ var badServiceTemplate = new ToscaServiceTemplate();
+ assertThrows(WebClientException.class, () -> apiHttpClient.createPolicy(badServiceTemplate));
}
@Test
void testCreatePolicyTypes() {
- assertDoesNotThrow(() -> apiHttpClient.createPolicyType(getTestToscaServiceTemplate()));
+ assertDoesNotThrow(() -> apiHttpClient.createPolicyType(serviceTemplate));
}
@Test
assertDoesNotThrow(() -> apiHttpClient.deletePolicy("dummyPolicy", "1.0.0"));
}
+ @Test
+ void testBadDeletePolicy() {
+ assertThrows(WebClientException.class, () -> apiHttpClient.deletePolicy("wrongPolicy", "1.0.0"));
+ }
+
@Test
void testDeletePolicyType() {
assertDoesNotThrow(() -> apiHttpClient.deletePolicyType("dummyPolicy", "1.0.0"));
@Test
void testInvalidEndpoint() {
- Response response = apiHttpClient.executePost("/invalid", Entity.entity(getTestToscaServiceTemplate(),
- MediaType.APPLICATION_JSON));
- assertThat(response.getStatus()).isEqualTo(404);
- }
-
- @Test
- void testInvalidClientParameter() {
- var parameters = new ParticipantPolicyParameters();
- assertThrows(AutomationCompositionRuntimeException.class,
- () -> new PolicyApiHttpClient(parameters));
- }
-
-
- private ToscaServiceTemplate getTestToscaServiceTemplate() {
- return new ToscaServiceTemplate();
+ assertThrows(WebClientException.class, () -> apiHttpClient.executePost("/invalid", serviceTemplate));
}
private static RestClientParameters getMockClientParameters(int port) {
- RestClientParameters params = new RestClientParameters();
- params.setName("policyClient");
+ var params = new RestClientParameters();
+ params.setClientName("policyClient");
params.setHostname("localhost");
+ params.setUserName("user");
+ params.setPassword("pwd");
params.setPort(port);
- params.setUseHttps(false);
return params;
}
-
-
-
}
/*-
* ============LICENSE_START=======================================================
- * Copyright (C) 2021-2024 Nordix Foundation.
+ * Copyright (C) 2021-2025 OpenInfra Foundation Europe. All rights reserved.
* ================================================================================
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
import static org.assertj.core.api.Assertions.assertThatThrownBy;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.Mockito.clearInvocations;
-import static org.mockito.Mockito.doReturn;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.verify;
+import static org.mockito.Mockito.when;
-import jakarta.ws.rs.core.Response;
import java.util.List;
import java.util.Map;
import java.util.UUID;
import org.onap.policy.models.tosca.authorative.concepts.ToscaPolicyType;
import org.onap.policy.models.tosca.authorative.concepts.ToscaServiceTemplate;
import org.onap.policy.models.tosca.authorative.concepts.ToscaTopologyTemplate;
+import org.springframework.http.HttpStatus;
+import org.springframework.web.reactive.function.client.WebClientResponseException;
class AutomationCompositionElementHandlerTest {
void testDeploy() throws PfModelException {
// Mock success scenario for policy creation and deployment
var api = mock(PolicyApiHttpClient.class);
- doReturn(Response.ok().build()).when(api).createPolicyType(any());
- doReturn(Response.ok().build()).when(api).createPolicy(any());
-
var pap = mock(PolicyPapHttpClient.class);
- doReturn(Response.accepted().build()).when(pap).handlePolicyDeployOrUndeploy(any(), any(), any());
-
var intermediaryApi = mock(ParticipantIntermediaryApi.class);
var handler = new AutomationCompositionElementHandler(api, pap, intermediaryApi);
"Undeployed");
}
+ @Test
+ void testDeployError() {
+ var api = mock(PolicyApiHttpClient.class);
+ var pap = mock(PolicyPapHttpClient.class);
+ var intermediaryApi = mock(ParticipantIntermediaryApi.class);
+ var handler = new AutomationCompositionElementHandler(api, pap, intermediaryApi);
+
+ var compositionElement = getCompositionElement();
+ var instanceElement = new InstanceElementDto(UUID.randomUUID(), UUID.randomUUID(),
+ Map.of("data_types", 100), Map.of());
+ assertThatThrownBy(() -> handler.deploy(compositionElement, instanceElement))
+ .isInstanceOf(PfModelException.class);
+ }
+
@Test
void testDeployNoPolicy() throws PfModelException {
var intermediaryApi = mock(ParticipantIntermediaryApi.class);
}
@Test
- void testApiException() throws PfModelException {
+ void testApiPolicyTypeException() throws PfModelException {
var api = mock(PolicyApiHttpClient.class);
- doReturn(Response.serverError().build()).when(api).createPolicyType(any());
- doReturn(Response.ok().build()).when(api).createPolicy(any());
+ when(api.createPolicyType(any()))
+ .thenThrow(new WebClientResponseException(HttpStatus.BAD_REQUEST.value(), "", null, null, null));
var pap = mock(PolicyPapHttpClient.class);
- doReturn(Response.accepted().build()).when(pap).handlePolicyDeployOrUndeploy(any(), any(), any());
-
var intermediaryApi = mock(ParticipantIntermediaryApi.class);
var handler = new AutomationCompositionElementHandler(api, pap, intermediaryApi);
}
@Test
- void testDeployPapException() {
+ void testApiPolicyException() throws PfModelException {
var api = mock(PolicyApiHttpClient.class);
- doReturn(Response.ok().build()).when(api).createPolicyType(any());
- doReturn(Response.ok().build()).when(api).createPolicy(any());
+ when(api.createPolicy(any()))
+ .thenThrow(new WebClientResponseException(HttpStatus.BAD_REQUEST.value(), "", null, null, null));
+
+ var pap = mock(PolicyPapHttpClient.class);
+ var intermediaryApi = mock(ParticipantIntermediaryApi.class);
+ var handler = new AutomationCompositionElementHandler(api, pap, intermediaryApi);
+
+ var compositionElement = getCompositionElement();
+ var instanceElement = getInstanceElement();
+ // Mock failure in policy creation
+ handler.deploy(compositionElement, instanceElement);
+ verify(intermediaryApi).updateAutomationCompositionElementState(instanceElement.instanceId(),
+ instanceElement.elementId(), DeployState.UNDEPLOYED, null, StateChangeResult.FAILED,
+ "Creation of PolicyTypes/Policies failed. Policies will not be deployed.");
+ }
+
+ @Test
+ void testDeployPapException() {
var pap = mock(PolicyPapHttpClient.class);
- doReturn(Response.serverError().build()).when(pap).handlePolicyDeployOrUndeploy(any(), any(), any());
+ when(pap.handlePolicyDeployOrUndeploy(any(), any(), any()))
+ .thenThrow(new WebClientResponseException(HttpStatus.BAD_REQUEST.value(), "", null, null, null));
var intermediaryApi = mock(ParticipantIntermediaryApi.class);
+ var api = mock(PolicyApiHttpClient.class);
var handler = new AutomationCompositionElementHandler(api, pap, intermediaryApi);
var compositionElement = getCompositionElement();
/*-
* ============LICENSE_START=======================================================
- * Copyright (C) 2021-2024 Nordix Foundation.
+ * Copyright (C) 2021--2025 OpenInfra Foundation Europe. All rights reserved.
* ================================================================================
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
package org.onap.policy.clamp.acm.participant.policy.main.parameters;
+import static org.junit.jupiter.api.Assertions.fail;
+
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import org.onap.policy.common.utils.coder.Coder;
import org.onap.policy.common.utils.coder.CoderException;
import org.onap.policy.common.utils.coder.StandardCoder;
+import org.onap.policy.common.utils.coder.StandardYamlCoder;
+import org.onap.policy.common.utils.resources.ResourceUtils;
+import org.onap.policy.models.tosca.authorative.concepts.ToscaServiceTemplate;
/**
* Class to hold/create all parameters for test cases.
public static final List<TopicParameters> SOURCE_TOPIC_PARAMS = List.of(getSinkTopicParams(), getSyncTopicParams());
public static final Coder CODER = new StandardCoder();
+ private static final StandardYamlCoder YAML_TRANSLATOR = new StandardYamlCoder();
/**
* Get ParticipantPolicyParameters.
public static UUID getParticipantId() {
return UUID.fromString("101c62b3-8918-41b9-a747-d21eb79c6c03");
}
+
+ /**
+ * Get ToscaServiceTemplate from resource.
+ *
+ * @param path path of the resource
+ */
+ public static ToscaServiceTemplate getToscaServiceTemplate(String path) {
+ try {
+ return YAML_TRANSLATOR.decode(ResourceUtils.getResourceAsStream(path), ToscaServiceTemplate.class);
+ } catch (CoderException e) {
+ fail("Cannot read or decode " + path);
+ return null;
+ }
+ }
}
+
<groupId>org.onap.policy.clamp</groupId>
<artifactId>policy-clamp-examples</artifactId>
<version>${project.version}</version>
+ <scope>test</scope>
</dependency>
<dependency>
<groupId>org.apache.kafka</groupId>