Policy client fixes
[clamp.git] / src / main / java / org / onap / clamp / clds / client / PolicyClient.java
1 /*-
2  * ============LICENSE_START=======================================================
3  * ONAP CLAMP
4  * ================================================================================
5  * Copyright (C) 2017 AT&T Intellectual Property. All rights
6  *                             reserved.
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
11  *
12  * http://www.apache.org/licenses/LICENSE-2.0
13  *
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============================================
20  * ===================================================================
21  * ECOMP is a trademark and service mark of AT&T Intellectual Property.
22  */
23
24 package org.onap.clamp.clds.client;
25
26 import com.att.eelf.configuration.EELFLogger;
27 import com.att.eelf.configuration.EELFManager;
28
29 import java.io.IOException;
30 import java.util.ArrayList;
31 import java.util.Collection;
32 import java.util.Collections;
33 import java.util.Date;
34 import java.util.List;
35 import java.util.Map;
36 import java.util.UUID;
37
38 import javax.ws.rs.BadRequestException;
39
40 import org.onap.clamp.clds.exception.policy.PolicyClientException;
41 import org.onap.clamp.clds.model.prop.ModelProperties;
42 import org.onap.clamp.clds.model.refprop.RefProp;
43 import org.onap.clamp.clds.util.LoggingUtils;
44 import org.onap.policy.api.AttributeType;
45 import org.onap.policy.api.ConfigRequestParameters;
46 import org.onap.policy.api.DeletePolicyCondition;
47 import org.onap.policy.api.DeletePolicyParameters;
48 import org.onap.policy.api.PolicyChangeResponse;
49 import org.onap.policy.api.PolicyConfig;
50 import org.onap.policy.api.PolicyConfigException;
51 import org.onap.policy.api.PolicyConfigType;
52 import org.onap.policy.api.PolicyEngine;
53 import org.onap.policy.api.PolicyEngineException;
54 import org.onap.policy.api.PolicyParameters;
55 import org.onap.policy.api.PolicyType;
56 import org.onap.policy.api.PushPolicyParameters;
57 import org.springframework.beans.factory.annotation.Autowired;
58 import org.springframework.beans.factory.annotation.Value;
59 import org.springframework.context.ApplicationContext;
60
61 /**
62  * Policy utility methods - specifically, send the policy.
63  */
64 public class PolicyClient {
65     protected static final String     POLICY_PREFIX_BASE         = "Config_";
66     protected static final String     POLICY_PREFIX_BRMS_PARAM   = "Config_BRMS_Param_";
67     protected static final String     POLICY_PREFIX_MICROSERVICE = "Config_MS_";
68
69     protected static final String     LOG_POLICY_PREFIX          = "Response is ";
70
71     protected static final EELFLogger logger                     = EELFManager.getInstance()
72             .getLogger(PolicyClient.class);
73     protected static final EELFLogger metricsLogger              = EELFManager.getInstance().getMetricsLogger();
74
75     @Value("${org.onap.clamp.config.files.cldsPolicyConfig:'classpath:/clds/clds-policy-config.properties'}")
76     protected String                  cldsPolicyConfigFile;
77
78     @Autowired
79     protected ApplicationContext      appContext;
80
81     @Autowired
82     protected RefProp                 refProp;
83
84     /**
85      * Perform BRMS policy type.
86      *
87      * @param attributes
88      *            A map of attributes
89      * @param prop
90      *            The ModelProperties
91      * @param policyRequestUuid
92      *            PolicyRequest UUID
93      * @return The response message of policy
94      * 
95      */
96     public String sendBrmsPolicy(Map<AttributeType, Map<String, String>> attributes, ModelProperties prop,
97             String policyRequestUuid) {
98
99         PolicyParameters policyParameters = new PolicyParameters();
100
101         // Set Policy Type(Mandatory)
102         policyParameters.setPolicyConfigType(PolicyConfigType.BRMS_PARAM);
103
104         // Set Policy Name(Mandatory)
105         policyParameters.setPolicyName(prop.getPolicyScopeAndNameWithUniqueId());
106
107         // documentation says this is options, but when tested, got the
108         // following failure: java.lang.Exception: Policy send failed: PE300 -
109         // Data Issue: No policyDescription given.
110         policyParameters.setPolicyDescription(refProp.getStringValue("op.policyDescription"));
111         policyParameters.setAttributes(attributes);
112         // Set a random UUID(Mandatory)
113         policyParameters.setRequestID(UUID.fromString(policyRequestUuid));
114         String policyNamePrefix = refProp.getStringValue("policy.op.policyNamePrefix");
115         String rtnMsg = send(policyParameters, prop, policyNamePrefix);
116
117         String policyType = refProp.getStringValue("policy.op.type");
118         push(policyType, prop);
119
120         return rtnMsg;
121     }
122
123     /**
124      * Perform send of microservice policy in JSON.
125      *
126      * @param policyJson
127      *            The policy JSON
128      * @param prop
129      *            The ModelProperties
130      * @param policyRequestUuid
131      *            The policy Request UUID
132      * @return The response message of policy
133      */
134     public String sendMicroServiceInJson(String policyJson, ModelProperties prop, String policyRequestUuid) {
135
136         PolicyParameters policyParameters = new PolicyParameters();
137
138         // Set Policy Type
139         policyParameters.setPolicyConfigType(PolicyConfigType.MicroService);
140         policyParameters.setEcompName(refProp.getStringValue("policy.onap.name"));
141         policyParameters.setPolicyName(prop.getCurrentPolicyScopeAndPolicyName());
142
143         policyParameters.setConfigBody(policyJson);
144         policyParameters.setConfigBodyType(PolicyType.JSON);
145
146         policyParameters.setRequestID(UUID.fromString(policyRequestUuid));
147         String policyNamePrefix = refProp.getStringValue("policy.ms.policyNamePrefix");
148
149         // Adding this line to clear the policy id from policy name while
150         // pushing to policy engine
151         prop.setPolicyUniqueId("");
152
153         String rtnMsg = send(policyParameters, prop, policyNamePrefix);
154         String policyType = refProp.getStringValue("policy.ms.type");
155         push(policyType, prop);
156
157         return rtnMsg;
158     }
159
160     /**
161      * Perform send of base policy in OTHER type.
162      *
163      * @param configBody
164      *            The config policy string body
165      * @param configPolicyName
166      *            The config policy name of the component that has been
167      *            pre-deployed in DCAE
168      * @param prop
169      *            The ModelProperties
170      * @param policyRequestUuid
171      *            The policy request UUID
172      * @return The answer from policy call
173      */
174     public String sendBasePolicyInOther(String configBody, String configPolicyName, ModelProperties prop,
175             String policyRequestUuid) {
176         PolicyParameters policyParameters = new PolicyParameters();
177
178         // Set Policy Type
179         policyParameters.setPolicyConfigType(PolicyConfigType.Base);
180         policyParameters.setEcompName(refProp.getStringValue("policy.onap.name"));
181         policyParameters.setPolicyName(prop.getCurrentPolicyScopeAndPolicyName());
182
183         policyParameters.setConfigBody(configBody);
184         policyParameters.setConfigBodyType(PolicyType.OTHER);
185         policyParameters.setConfigName("HolmesPolicy");
186         policyParameters.setPolicyName(configPolicyName);
187
188         policyParameters.setRequestID(UUID.fromString(policyRequestUuid));
189
190         // Adding this line to clear the policy id from policy name while
191         // pushing to policy engine
192         prop.setPolicyUniqueId("");
193
194         String rtnMsg = send(policyParameters, prop, POLICY_PREFIX_BASE);
195         push(PolicyConfigType.Base.toString(), prop);
196
197         return rtnMsg;
198     }
199
200     /**
201      * Perform send of Microservice policy in OTHER type.
202      * 
203      * @param configBody
204      *            The config policy string body
205      * @param prop
206      *            The ModelProperties
207      * @param policyRequestUuid
208      *            The policy request UUID
209      * @return The answer from policy call
210      */
211     public String sendMicroServiceInOther(String configBody, ModelProperties prop, String policyRequestUuid) {
212
213         PolicyParameters policyParameters = new PolicyParameters();
214         // Set Policy Type 
215         policyParameters.setPolicyConfigType(PolicyConfigType.MicroService);
216         policyParameters.setOnapName("DCAE");
217         policyParameters.setEcompName(refProp.getStringValue("policy.onap.name"));
218         policyParameters.setPolicyName(prop.getCurrentPolicyScopeAndPolicyName());
219         policyParameters.setConfigBody(configBody);
220         String policyNamePrefix = refProp.getStringValue("policy.ms.policyNamePrefix");
221
222         // Adding this line to clear the policy id from policy name while
223         // pushing to policy engine
224         prop.setPolicyUniqueId("");
225
226         String rtnMsg = send(policyParameters, prop, policyNamePrefix);
227         String policyType = refProp.getStringValue("policy.ms.type");
228         push(policyType, prop);
229
230         return rtnMsg;
231     }
232
233     /**
234      * Perform send of policy.
235      *
236      * @param policyParameters
237      *            The PolicyParameters
238      * @param prop
239      *            The ModelProperties
240      * @return The response message of Policy
241      */
242     protected String send(PolicyParameters policyParameters, ModelProperties prop, String policyNamePrefix) {
243         // Verify whether it is triggered by Validation Test button from UI
244         if (prop.isTest()) {
245             return "send not executed for test action";
246         }
247
248         // API method to create or update Policy.
249         PolicyChangeResponse response = null;
250         String responseMessage = "";
251         Date startTime = new Date();
252         try {
253             List<Integer> versions = getVersions(policyNamePrefix, prop);
254             if (versions.isEmpty()) {
255                 LoggingUtils.setTargetContext("Policy", "createPolicy");
256                 logger.info("Attempting to create policy for action=" + prop.getActionCd());
257                 response = getPolicyEngine().createPolicy(policyParameters);
258                 responseMessage = response.getResponseMessage();
259             } else {
260                 LoggingUtils.setTargetContext("Policy", "updatePolicy");
261                 logger.info("Attempting to update policy for action=" + prop.getActionCd());
262                 response = getPolicyEngine().updatePolicy(policyParameters);
263                 responseMessage = response.getResponseMessage();
264             }
265         } catch (Exception e) {
266             logger.error("Exception occurred during policy communication", e);
267             throw new PolicyClientException("Exception while communicating with Policy", e);
268         }
269         logger.info(LOG_POLICY_PREFIX + responseMessage);
270
271         LoggingUtils.setTimeContext(startTime, new Date());
272
273         if (response.getResponseCode() == 200) {
274             logger.info("Policy send successful");
275             metricsLogger.info("Policy send success");
276         } else {
277             logger.warn("Policy send failed: " + responseMessage);
278             metricsLogger.info("Policy send failure");
279             throw new BadRequestException("Policy send failed: " + responseMessage);
280         }
281
282         return responseMessage;
283     }
284
285     /**
286      * Format and send push of policy.
287      *
288      * @param policyType
289      *            The policy Type
290      * @param prop
291      *            The ModelProperties
292      * @return The response message of policy
293      */
294     protected String push(String policyType, ModelProperties prop) {
295         // Verify whether it is triggered by Validation Test button from UI
296         if (prop.isTest()) {
297             return "push not executed for test action";
298         }
299
300         PushPolicyParameters pushPolicyParameters = new PushPolicyParameters();
301
302         // Parameter arguments
303         if (prop.getPolicyUniqueId() != null && !prop.getPolicyUniqueId().isEmpty()) {
304             pushPolicyParameters.setPolicyName(prop.getPolicyScopeAndNameWithUniqueId());
305         } else {
306             pushPolicyParameters.setPolicyName(prop.getCurrentPolicyScopeAndPolicyName());
307         }
308         logger.info("Policy Name in Push policy method - " + pushPolicyParameters.getPolicyName());
309
310         pushPolicyParameters.setPolicyType(policyType);
311         pushPolicyParameters.setPdpGroup(refProp.getStringValue("policy.pdp.group"));
312         pushPolicyParameters.setRequestID(null);
313
314         // API method to create or update Policy.
315         PolicyChangeResponse response = null;
316         String responseMessage = "";
317         try {
318             logger.info("Attempting to push policy...");
319             response = getPolicyEngine().pushPolicy(pushPolicyParameters);
320             responseMessage = response.getResponseMessage();
321         } catch (Exception e) {
322             logger.error("Exception occurred during policy communication", e);
323             throw new PolicyClientException("Exception while communicating with Policy", e);
324         }
325         logger.info(LOG_POLICY_PREFIX + responseMessage);
326
327         if (response != null && (response.getResponseCode() == 200 || response.getResponseCode() == 204)) {
328             logger.info("Policy push successful");
329         } else {
330             logger.warn("Policy push failed: " + responseMessage);
331             throw new BadRequestException("Policy push failed: " + responseMessage);
332         }
333
334         return responseMessage;
335     }
336
337     /**
338      * Use Get Config Policy API to retrieve the versions for a policy. Return
339      * versions in sorted order. Return empty list if none found.
340      *
341      * @param policyNamePrefix
342      *            The Policy Name Prefix
343      * @param prop
344      *            The ModelProperties
345      * @return The response message from policy
346      * @throws PolicyConfigException
347      *             In case of issues with policy engine
348      */
349     protected List<Integer> getVersions(String policyNamePrefix, ModelProperties prop) throws PolicyConfigException {
350
351         ArrayList<Integer> versions = new ArrayList<>();
352         ConfigRequestParameters configRequestParameters = new ConfigRequestParameters();
353         String policyName = "";
354
355         if (prop.getPolicyUniqueId() != null && !prop.getPolicyUniqueId().isEmpty()) {
356             policyName = prop.getCurrentPolicyScopeAndFullPolicyName(policyNamePrefix) + "_" + prop.getPolicyUniqueId();
357         } else {
358             policyName = prop.getCurrentPolicyScopeAndFullPolicyName(policyNamePrefix);
359         }
360
361         logger.info("policyName=" + policyName);
362         configRequestParameters.setPolicyName(policyName);
363         try {
364             Collection<PolicyConfig> response = getPolicyEngine().getConfig(configRequestParameters);
365             for (PolicyConfig policyConfig : response) {
366                 Integer version = Integer.valueOf(policyConfig.getPolicyVersion());
367                 versions.add(version);
368             }
369             Collections.sort(versions);
370             logger.info("Policy versions.size()=" + versions.size());
371         } catch (PolicyConfigException e) {
372             // just print warning - if no policy version found
373             logger.warn("warning: policy not found...policy name - " + policyName, e.getMessage());
374         }
375         return versions;
376
377     }
378
379     /**
380      * This method create a new policy engine.
381      * 
382      * @return A new policy engine
383      */
384     private PolicyEngine getPolicyEngine() {
385         PolicyEngine policyEngine;
386         try {
387             policyEngine = new PolicyEngine(appContext.getResource(cldsPolicyConfigFile).getFile().getAbsolutePath());
388         } catch (IOException e1) {
389             throw new PolicyClientException("Exception when opening policy config file", e1);
390         } catch (PolicyEngineException e) {
391             throw new PolicyClientException("Exception when creating a new policy engine", e);
392         }
393         return policyEngine;
394     }
395
396     /**
397      * Format and send delete Micro Service requests to Policy.
398      *
399      * @param prop
400      *            The ModelProperties
401      * @return The response message from Policy
402      */
403     public String deleteMicrosService(ModelProperties prop) {
404         String policyType = refProp.getStringValue("policy.ms.type");
405         return deletePolicy(prop, policyType);
406     }
407
408     /**
409      * This method delete the Base policy.
410      *
411      * @param prop
412      *            The model Properties
413      * @return A string with the answer from policy
414      */
415     public String deleteBasePolicy(ModelProperties prop) {
416         return deletePolicy(prop, PolicyConfigType.Base.toString());
417     }
418
419     /**
420      * Format and send delete BRMS requests to Policy.
421      *
422      * @param prop
423      *            The ModelProperties
424      * @return The response message from policy
425      */
426     public String deleteBrms(ModelProperties prop) {
427         String policyType = refProp.getStringValue("policy.op.type");
428         return deletePolicy(prop, policyType);
429     }
430
431     /**
432      * Format and send delete PAP and PDP requests to Policy.
433      *
434      * @param prop
435      *            The ModelProperties
436      *
437      * @return The response message from policy
438      */
439     protected String deletePolicy(ModelProperties prop, String policyType) {
440         DeletePolicyParameters deletePolicyParameters = new DeletePolicyParameters();
441
442         if (prop.getPolicyUniqueId() != null && !prop.getPolicyUniqueId().isEmpty()) {
443             deletePolicyParameters.setPolicyName(prop.getPolicyScopeAndNameWithUniqueId());
444         } else {
445             deletePolicyParameters.setPolicyName(prop.getCurrentPolicyScopeAndPolicyName());
446         }
447         logger.info("Policy Name in delete policy method - " + deletePolicyParameters.getPolicyName());
448         deletePolicyParameters.setPolicyComponent("PDP");
449         deletePolicyParameters.setDeleteCondition(DeletePolicyCondition.ALL);
450         deletePolicyParameters.setPdpGroup(refProp.getStringValue("policy.pdp.group"));
451         deletePolicyParameters.setPolicyType(policyType);
452         // send delete request
453         StringBuilder responseMessage = new StringBuilder(sendDeletePolicy(deletePolicyParameters, prop));
454
455         logger.info("Deleting policy from PAP...");
456         deletePolicyParameters.setPolicyComponent("PAP");
457         deletePolicyParameters.setDeleteCondition(DeletePolicyCondition.ALL);
458
459         // send delete request
460         responseMessage.append(sendDeletePolicy(deletePolicyParameters, prop));
461
462         return responseMessage.toString();
463     }
464
465     /**
466      * Send delete request to Policy.
467      *
468      * @param deletePolicyParameters
469      *            The DeletePolicyParameters
470      * @param prop
471      *            The ModelProperties
472      * @return The response message from policy
473      */
474     protected String sendDeletePolicy(DeletePolicyParameters deletePolicyParameters, ModelProperties prop) {
475         // Verify whether it is triggered by Validation Test button from UI
476         if (prop.isTest()) {
477             return "delete not executed for test action";
478         }
479
480         // API method to create or update Policy.
481         PolicyChangeResponse response = null;
482         String responseMessage = "";
483         try {
484             logger.info("Attempting to delete policy...");
485             response = getPolicyEngine().deletePolicy(deletePolicyParameters);
486             responseMessage = response.getResponseMessage();
487         } catch (Exception e) {
488             logger.error("Exception occurred during policy communnication", e);
489         }
490         logger.info(LOG_POLICY_PREFIX + responseMessage);
491
492         if (response != null && response.getResponseCode() == 200) {
493             logger.info("Policy delete successful");
494         } else {
495             logger.warn("Policy delete failed: " + responseMessage);
496             throw new BadRequestException("Policy delete failed: " + responseMessage);
497         }
498
499         return responseMessage;
500     }
501 }