2 * ============LICENSE_START=======================================================
4 * ================================================================================
5 * Copyright (C) 2019-2021 AT&T Intellectual Property. All rights reserved.
6 * Modifications Copyright (C) 2021 Nordix Foundation.
7 * ================================================================================
8 * Licensed under the Apache License, Version 2.0 (the "License");
9 * you may not use this file except in compliance with the License.
10 * You may obtain a copy of the License at
12 * http://www.apache.org/licenses/LICENSE-2.0
14 * Unless required by applicable law or agreed to in writing, software
15 * distributed under the License is distributed on an "AS IS" BASIS,
16 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17 * See the License for the specific language governing permissions and
18 * limitations under the License.
19 * ============LICENSE_END=========================================================
22 package org.onap.policy.pap.main.comm.msgdata;
24 import java.util.Collection;
25 import java.util.Collections;
26 import java.util.HashMap;
27 import java.util.HashSet;
28 import java.util.LinkedList;
29 import java.util.List;
32 import java.util.stream.Collectors;
34 import org.apache.commons.lang3.StringUtils;
35 import org.onap.policy.models.pdp.concepts.PdpMessage;
36 import org.onap.policy.models.pdp.concepts.PdpStatus;
37 import org.onap.policy.models.pdp.concepts.PdpUpdate;
38 import org.onap.policy.models.tosca.authorative.concepts.ToscaConceptIdentifier;
39 import org.onap.policy.models.tosca.authorative.concepts.ToscaPolicy;
40 import org.onap.policy.pap.main.parameters.RequestParams;
41 import org.slf4j.Logger;
42 import org.slf4j.LoggerFactory;
48 public class UpdateReq extends RequestImpl {
50 private static final Logger logger = LoggerFactory.getLogger(RequestImpl.class);
53 * Policies to be undeployed if the request fails.
56 private Collection<ToscaConceptIdentifier> undeployPolicies = Collections.emptyList();
59 * Constructs the object, and validates the parameters.
61 * @param params configuration parameters
62 * @param name the request name, used for logging purposes
63 * @param message the initial message
65 * @throws IllegalArgumentException if a required parameter is not set
67 public UpdateReq(RequestParams params, String name, PdpUpdate message) {
68 super(params, name, message);
72 public PdpUpdate getMessage() {
73 return (PdpUpdate) super.getMessage();
77 public String checkResponse(PdpStatus response) {
79 undeployPolicies = Collections.emptyList();
81 String reason = super.checkResponse(response);
83 // response isn't for this PDP - don't generate notifications
87 PdpUpdate message = getMessage();
89 if (!StringUtils.equals(message.getPdpGroup(), response.getPdpGroup())) {
90 return "group does not match";
93 if (!StringUtils.equals(message.getPdpSubgroup(), response.getPdpSubgroup())) {
94 return "subgroup does not match";
97 if (message.getPdpSubgroup() == null) {
101 Set<ToscaConceptIdentifier> actualSet = new HashSet<>(alwaysList(response.getPolicies()));
102 Set<ToscaConceptIdentifier> expectedSet = new HashSet<>(alwaysList(message.getPoliciesToBeDeployed()).stream()
103 .map(ToscaPolicy::getIdentifier).collect(Collectors.toSet()));
105 getNotifier().processResponse(response.getName(), message.getPdpGroup(), expectedSet, actualSet);
107 Set<ToscaConceptIdentifier> expectedUndeploySet =
108 new HashSet<>(alwaysList(message.getPoliciesToBeUndeployed()));
110 if (actualSet.stream().anyMatch(expectedUndeploySet::contains)) {
111 logger.info("some policies have failed to undeploy");
114 if (!actualSet.containsAll(expectedSet)) {
115 // need to undeploy the policies that are expected, but missing from the
117 undeployPolicies = expectedSet;
118 undeployPolicies.removeAll(actualSet);
120 return "policies do not match";
127 public boolean reconfigure(PdpMessage newMessage) {
128 if (!(newMessage instanceof PdpUpdate)) {
129 // not an update - no change to this request
133 PdpUpdate update = (PdpUpdate) newMessage;
135 if (isSameContent(update)) {
136 // content hasn't changed - nothing more to do
140 Map<ToscaConceptIdentifier, ToscaPolicy> newDeployMap = update.getPoliciesToBeDeployed().stream()
141 .collect(Collectors.toMap(ToscaPolicy::getIdentifier, policy -> policy));
143 // Merge undpeloy lists
144 Set<ToscaConceptIdentifier> policiesToBeUndeployedSet = new HashSet<>(getMessage().getPoliciesToBeUndeployed());
145 policiesToBeUndeployedSet.removeAll(newDeployMap.keySet());
146 policiesToBeUndeployedSet.addAll(update.getPoliciesToBeUndeployed());
147 final List<ToscaConceptIdentifier> policiestoBeUndeployed = new LinkedList<>(policiesToBeUndeployedSet);
149 // Merge deploy lists
150 Map<ToscaConceptIdentifier, ToscaPolicy> policiesToBeDeployedMap = getMessage().getPoliciesToBeDeployed()
151 .stream().collect(Collectors.toMap(ToscaPolicy::getIdentifier, policy -> policy));
152 policiesToBeDeployedMap.keySet().removeAll(update.getPoliciesToBeUndeployed());
153 policiesToBeDeployedMap.putAll(newDeployMap);
154 final List<ToscaPolicy> policiesToBeDeployed = new LinkedList<>(policiesToBeDeployedMap.values());
156 // Set lists in update
157 update.setPoliciesToBeDeployed(policiesToBeDeployed);
158 update.setPoliciesToBeUndeployed(policiestoBeUndeployed);
160 reconfigure2(update);
164 protected final boolean isSameContent(PdpUpdate second) {
165 PdpUpdate first = getMessage();
167 if (!StringUtils.equals(first.getPdpGroup(), second.getPdpGroup())) {
171 if (!StringUtils.equals(first.getPdpSubgroup(), second.getPdpSubgroup())) {
175 // see if the policies are the same
176 Set<ToscaPolicy> set1 = new HashSet<>(alwaysList(first.getPoliciesToBeDeployed()));
177 Set<ToscaPolicy> set2 = new HashSet<>(alwaysList(second.getPoliciesToBeDeployed()));
179 if (!(set1.equals(set2))) {
183 Set<ToscaConceptIdentifier> undep1 = new HashSet<>(alwaysList(first.getPoliciesToBeUndeployed()));
184 Set<ToscaConceptIdentifier> undep2 = new HashSet<>(alwaysList(second.getPoliciesToBeUndeployed()));
186 return undep1.equals(undep2);
190 * Always get a list, even if the original is {@code null}.
192 * @param list the original list, or {@code null}
193 * @return the list, or an empty list if the original was {@code null}
195 private <T> List<T> alwaysList(List<T> list) {
196 return (list != null ? list : Collections.emptyList());