2 * ============LICENSE_START=======================================================
4 * ================================================================================
5 * Copyright (C) 2017-2019 AT&T Intellectual Property. All rights reserved.
6 * ================================================================================
7 * Licensed under the Apache License, Version 2.0 (the "License");
8 * you may not use this file except in compliance with the License.
9 * You may obtain a copy of the License at
11 * http://www.apache.org/licenses/LICENSE-2.0
13 * Unless required by applicable law or agreed to in writing, software
14 * distributed under the License is distributed on an "AS IS" BASIS,
15 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16 * See the License for the specific language governing permissions and
17 * limitations under the License.
18 * ============LICENSE_END=========================================================
20 package org.onap.policy.pap.xacml.rest.handler;
22 import com.att.research.xacml.api.pap.PAPException;
23 import com.att.research.xacml.api.pap.PDPPolicy;
24 import com.att.research.xacml.util.XACMLProperties;
26 import java.io.IOException;
27 import java.sql.SQLException;
28 import java.util.List;
29 import javax.script.SimpleBindings;
30 import javax.servlet.http.HttpServletRequest;
31 import javax.servlet.http.HttpServletResponse;
32 import org.onap.policy.common.logging.ONAPLoggingContext;
33 import org.onap.policy.common.logging.eelf.MessageCodes;
34 import org.onap.policy.common.logging.eelf.PolicyLogger;
35 import org.onap.policy.common.logging.flexlogger.FlexLogger;
36 import org.onap.policy.common.logging.flexlogger.Logger;
37 import org.onap.policy.pap.xacml.rest.XACMLPapServlet;
38 import org.onap.policy.pap.xacml.rest.components.PolicyDBDaoTransaction;
39 import org.onap.policy.pap.xacml.rest.elk.client.PolicyElasticSearchController;
40 import org.onap.policy.pap.xacml.rest.model.RemoveGroupPolicy;
41 import org.onap.policy.pap.xacml.rest.util.JPAUtils;
42 import org.onap.policy.rest.adapter.PolicyRestAdapter;
43 import org.onap.policy.rest.dao.CommonClassDao;
44 import org.onap.policy.rest.jpa.PolicyEntity;
45 import org.onap.policy.rest.jpa.PolicyVersion;
46 import org.onap.policy.utils.PolicyUtils;
47 import org.onap.policy.xacml.api.XACMLErrorConstants;
48 import org.onap.policy.xacml.api.pap.OnapPDPGroup;
49 import org.onap.policy.xacml.std.pap.StdPAPPolicy;
50 import org.onap.policy.xacml.std.pap.StdPDPGroup;
51 import org.springframework.beans.factory.annotation.Autowired;
52 import org.springframework.stereotype.Component;
55 public class DeleteHandler {
57 private static CommonClassDao commonClassDao;
60 public DeleteHandler(CommonClassDao commonClassDao) {
61 DeleteHandler.commonClassDao = commonClassDao;
64 public DeleteHandler() {
65 // Default Constructor
68 private OnapPDPGroup newgroup;
69 private static Logger logger = FlexLogger.getLogger(DeleteHandler.class);
70 public static final String POLICY_IN_PDP = "PolicyInPDP";
71 public static final String ERROR = "error";
72 public static final String UNKNOWN = "unknown";
73 private static final String REGEX = "[0-9a-zA-Z._]*";
75 public void doAPIDeleteFromPAP(HttpServletRequest request, HttpServletResponse response)
76 throws IOException, SQLException {
77 // get the request content into a String
79 java.util.Scanner scanner = new java.util.Scanner(request.getInputStream());
80 scanner.useDelimiter("\\A");
81 json = scanner.hasNext() ? scanner.next() : "";
83 PolicyLogger.info("JSON request from API to Delete Policy from the PAP: " + json);
84 // convert Object sent as JSON into local object
85 StdPAPPolicy policy = PolicyUtils.jsonStringToObject(json, StdPAPPolicy.class);
86 String policyName = policy.getPolicyName();
87 boolean policyVersionDeleted = false;
88 String removeXMLExtension;
90 String removeVersionExtension;
91 String splitPolicyName = null;
92 String[] split = null;
93 String status = ERROR;
94 PolicyEntity policyEntity = null;
95 JPAUtils jpaUtils = null;
98 jpaUtils = JPAUtils.getJPAUtilsInstance();
99 } catch (Exception e) {
100 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "XACMLPapServlet",
101 " Could not create JPAUtils instance on the PAP");
102 response.addHeader(ERROR, "jpautils");
103 response.addHeader("operation", "delete");
104 response.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
107 if (jpaUtils.dbLockdownIgnoreErrors()) {
108 PolicyLogger.warn("Policies are locked down");
109 response.addHeader("operation", "delete");
110 response.addHeader("lockdown", "true");
111 response.setStatus(HttpServletResponse.SC_ACCEPTED);
114 String policyEntityQuery = null;
116 if (policyName.endsWith(".xml")) {
117 removeXMLExtension = policyName.replace(".xml", "");
119 Integer.parseInt(removeXMLExtension.substring(removeXMLExtension.lastIndexOf('.') + 1));
120 removeVersionExtension = removeXMLExtension.substring(0, removeXMLExtension.lastIndexOf('.'));
121 boolean queryCheck = true;
122 if (policy.getDeleteCondition().equalsIgnoreCase("All Versions")) {
123 if (policyName.contains("Config_")) {
124 splitPolicyName = removeVersionExtension.replace(".Config_", ":Config_");
125 } else if (policyName.contains("Action_")) {
126 splitPolicyName = removeVersionExtension.replace(".Action_", ":Action_");
127 } else if (policyName.contains("Decision_")) {
128 splitPolicyName = removeVersionExtension.replace(".Decision_", ":Decision_");
130 if (splitPolicyName != null) {
131 split = splitPolicyName.split(":");
133 PolicyLogger.error(MessageCodes.ERROR_UNKNOWN +
134 "Failed to delete the policy. Please, provide the valid policyname.");
135 response.addHeader(ERROR, UNKNOWN);
136 response.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
140 "SELECT p FROM PolicyEntity p WHERE p.policyName LIKE :pName and p.scope=:pScope";
141 } else if (policy.getDeleteCondition().equalsIgnoreCase("Current Version")) {
142 if (policyName.contains("Config_")) {
143 splitPolicyName = policyName.replace(".Config_", ":Config_");
144 } else if (policyName.contains("Action_")) {
145 splitPolicyName = policyName.replace(".Action_", ":Action_");
146 } else if (policyName.contains("Decision_")) {
147 splitPolicyName = policyName.replace(".Decision_", ":Decision_");
149 split = splitPolicyName.split(":");
151 policyEntityQuery = "SELECT p FROM PolicyEntity p WHERE p.policyName=:pName and p.scope=:pScope";
153 SimpleBindings params = new SimpleBindings();
155 params.put("pName", "%" + split[1] + "%");
157 params.put("pName", split[1]);
160 params.put("pScope", split[0]);
161 List<?> peResult = commonClassDao.getDataByQuery(policyEntityQuery, params);
162 if (!peResult.isEmpty()) {
163 String getPolicyVersion = "Select p from PolicyVersion p where p.policyName=:pname";
164 SimpleBindings pvParams = new SimpleBindings();
165 pvParams.put("pname", removeVersionExtension.replace(".", File.separator));
166 List<?> pvResult = commonClassDao.getDataByQuery(getPolicyVersion, pvParams);
167 PolicyVersion pVersion = (PolicyVersion) pvResult.get(0);
169 if (policy.getDeleteCondition().equalsIgnoreCase("All Versions")) {
170 boolean groupCheck = checkPolicyGroupEntity(peResult);
172 for (Object peData : peResult) {
173 policyEntity = (PolicyEntity) peData;
174 status = deletePolicyEntityData(policyEntity);
177 status = POLICY_IN_PDP;
181 PolicyLogger.error(MessageCodes.ERROR_DATA_ISSUE +
182 "Exception Occured while deleting the Entity from Database.");
183 response.addHeader(ERROR, UNKNOWN);
184 response.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
187 PolicyLogger.error(MessageCodes.GENERAL_WARNING +
188 "Policy can't be deleted, it is active in PDP Groups.");
189 response.addHeader(ERROR, POLICY_IN_PDP);
190 response.setStatus(HttpServletResponse.SC_CONFLICT);
194 policyVersionDeleted = true;
195 commonClassDao.delete(pVersion);
196 } catch (Exception e) {
197 logger.error(e.getMessage(), e);
198 policyVersionDeleted = false;
202 } else if (policy.getDeleteCondition().equalsIgnoreCase("Current Version")) {
203 boolean groupCheck = checkPolicyGroupEntity(peResult);
205 policyEntity = (PolicyEntity) peResult.get(0);
206 status = deletePolicyEntityData(policyEntity);
208 status = POLICY_IN_PDP;
211 if (ERROR.equals(status)) {
212 PolicyLogger.error(MessageCodes.ERROR_DATA_ISSUE +
213 "Exception Occured while deleting the Entity from Database.");
214 response.addHeader(ERROR, UNKNOWN);
215 response.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
217 } else if (POLICY_IN_PDP.equals(status)) {
218 PolicyLogger.error(MessageCodes.GENERAL_WARNING +
219 "Policy can't be deleted, it is active in PDP Groups.");
220 response.addHeader(ERROR, POLICY_IN_PDP);
221 response.setStatus(HttpServletResponse.SC_CONFLICT);
224 if (currentVersion > 1) {
225 if (!peResult.isEmpty()) {
226 for (Object object : peResult) {
227 policyEntity = (PolicyEntity) object;
228 String policyEntityName = policyEntity.getPolicyName().replace(".xml", "");
229 int policyEntityVersion = Integer.parseInt(
230 policyEntityName.substring(policyEntityName.lastIndexOf('.') + 1));
231 if (policyEntityVersion > newVersion) {
232 newVersion = policyEntityVersion - 1;
236 pVersion.setActiveVersion(newVersion);
237 pVersion.setHigherVersion(newVersion);
239 policyVersionDeleted = true;
240 commonClassDao.save(pVersion);
241 } catch (Exception e) {
242 logger.error(e.getMessage(), e);
243 policyVersionDeleted = false;
247 policyVersionDeleted = true;
248 commonClassDao.delete(pVersion);
249 } catch (Exception e) {
250 logger.error(e.getMessage(), e);
251 policyVersionDeleted = false;
257 PolicyLogger.error(MessageCodes.ERROR_UNKNOWN +
258 "Failed to delete the policy for an unknown reason. Check the file system and other logs" +
259 " for further information.");
260 response.addHeader(ERROR, UNKNOWN);
261 response.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
265 } catch (Exception e) {
266 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "XACMLPapServlet", " ERROR");
267 response.addHeader(ERROR, "deleteDB");
268 response.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
272 if (policyVersionDeleted) {
273 response.setStatus(HttpServletResponse.SC_OK);
274 response.addHeader("successMapKey", "success");
275 response.addHeader("operation", "delete");
277 PolicyLogger.error(MessageCodes.ERROR_UNKNOWN +
278 "Failed to delete the policy for an unknown reason. Check the file system and other logs for " +
279 "further information.");
280 response.addHeader(ERROR, UNKNOWN);
281 response.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
285 public static String deletePolicyEntityData(PolicyEntity policyEntity) {
286 PolicyElasticSearchController controller = new PolicyElasticSearchController();
287 PolicyRestAdapter policyData = new PolicyRestAdapter();
288 String policyName = policyEntity.getPolicyName();
290 if (policyName.contains("Config_") || policyName.contains("Decision_MS_")) {
291 commonClassDao.delete(policyEntity.getConfigurationData());
292 } else if (policyName.contains("Action_")) {
293 commonClassDao.delete(policyEntity.getActionBodyEntity());
295 String searchPolicyName = policyEntity.getScope() + "." + policyEntity.getPolicyName();
296 policyData.setNewFileName(searchPolicyName);
297 controller.deleteElk(policyData);
298 commonClassDao.delete(policyEntity);
299 } catch (Exception e) {
300 logger.error(e.getMessage(), e);
306 public static boolean checkPolicyGroupEntity(List<?> peResult) {
307 String groupEntityquery = "from PolicyGroupEntity where policyid = :policyEntityId";
308 for (Object peData : peResult) {
309 PolicyEntity policyEntity = (PolicyEntity) peData;
310 SimpleBindings geParams = new SimpleBindings();
311 geParams.put("policyEntityId", policyEntity.getPolicyId());
312 List<Object> groupobject = commonClassDao.getDataByQuery(groupEntityquery, geParams);
313 if (!groupobject.isEmpty()) {
320 public void doAPIDeleteFromPDP(HttpServletRequest request, HttpServletResponse response,
321 ONAPLoggingContext loggingContext) throws IOException {
323 String policyName = request.getParameter("policyName");
324 String groupId = request.getParameter("groupId");
325 String responseString = null;
327 if (groupId != null && !groupId.matches(REGEX)) {
328 response.setStatus(HttpServletResponse.SC_BAD_REQUEST);
329 response.addHeader("error", ERROR);
330 response.addHeader("message", "Group Id is not valid");
334 PolicyLogger.info("JSON request from API to Delete Policy from the PDP: " + policyName);
336 // for PUT operations the group may or may not need to exist before the operation can be done
337 OnapPDPGroup group = null;
339 group = XACMLPapServlet.getPAPEngine().getGroup(groupId);
340 } catch (PAPException e) {
341 PolicyLogger.error("Exception occured While PUT operation is performing for PDP Group" + e);
344 String message = "Unknown groupId '" + groupId + "'.";
345 PolicyLogger.error(MessageCodes.ERROR_DATA_ISSUE + " " + message);
346 loggingContext.transactionEnded();
347 PolicyLogger.audit("Transaction Failed - See Error.log");
348 response.addHeader(ERROR, "UnknownGroup");
349 response.addHeader("message", message);
350 response.setStatus(HttpServletResponse.SC_NOT_FOUND);
353 loggingContext.setServiceName("API:PAP.deletPolicyFromPDPGroup");
354 if (policyName.contains("xml")) {
356 .debug("The full file name including the extension was provided for policyName.. continue.");
358 String message = XACMLErrorConstants.ERROR_DATA_ISSUE + "Invalid policyName... "
359 + "policyName must be the full name of the file to be deleted including version and extension";
360 PolicyLogger.error(MessageCodes.ERROR_DATA_ISSUE + " Invalid policyName... "
361 + "policyName must be the full name of the file to be deleted including version and extension");
362 response.addHeader(ERROR, message);
363 response.setStatus(HttpServletResponse.SC_BAD_REQUEST);
366 RemoveGroupPolicy removePolicy = new RemoveGroupPolicy((StdPDPGroup) group);
367 PDPPolicy policy = group.getPolicy(policyName);
368 if (policy != null) {
370 if ((policy.getId().contains("Config_MS_")) || (policy.getId().contains("BRMS_Param"))) {
371 if (preSafetyCheck(policy)) {
372 PolicyLogger.debug("Precheck Successful.");
375 PolicyLogger.info("Preparing to remove policy from group: " + group.getId());
376 removePolicy.prepareToRemove(policy);
377 OnapPDPGroup updatedGroup = removePolicy.getUpdatedObject();
378 responseString = deletePolicyFromPDPGroup(updatedGroup, loggingContext);
380 String message = XACMLErrorConstants.ERROR_DATA_ISSUE + "Policy does not exist on the PDP.";
381 PolicyLogger.error(message);
382 PolicyLogger.error(MessageCodes.ERROR_DATA_ISSUE + " Policy does not exist on the PDP.");
383 response.addHeader(ERROR, message);
384 response.setStatus(HttpServletResponse.SC_BAD_REQUEST);
388 switch (responseString) {
390 loggingContext.transactionEnded();
391 PolicyLogger.info("Policy successfully deleted!");
392 PolicyLogger.audit("Policy successfully deleted!");
393 response.setStatus(HttpServletResponse.SC_OK);
394 response.addHeader("successMapKey", "success");
395 response.addHeader("operation", "delete");
398 String message = XACMLErrorConstants.ERROR_DATA_ISSUE + "Group update had bad input.";
399 PolicyLogger.error(MessageCodes.ERROR_DATA_ISSUE + " Group update had bad input.");
400 response.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
401 response.addHeader(ERROR, "groupUpdate");
402 response.addHeader("message", message);
405 PolicyLogger.error(MessageCodes.ERROR_PROCESS_FLOW + " Error while updating group in the database");
406 response.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
407 response.addHeader(ERROR, "deleteDB");
410 PolicyLogger.error(MessageCodes.ERROR_UNKNOWN +
411 " Failed to delete the policy for an unknown reason. Check the file system and other logs " +
413 "further information.");
414 response.addHeader(ERROR, UNKNOWN);
415 response.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
420 private String deletePolicyFromPDPGroup(OnapPDPGroup group, ONAPLoggingContext loggingContext) {
421 PolicyDBDaoTransaction acPutTransaction = XACMLPapServlet.getDbDaoTransaction();
422 String response = null;
423 loggingContext.setServiceName("API:PAP.DeleteHandler");
424 OnapPDPGroup existingGroup = null;
426 existingGroup = XACMLPapServlet.getPAPEngine().getGroup(group.getId());
427 } catch (PAPException e1) {
428 PolicyLogger.error("Exception occured While Deleting Policy From PDP Group" + e1);
430 if (!(group instanceof StdPDPGroup) || existingGroup == null ||
431 !(group.getId().equals(existingGroup.getId()))) {
432 String existingID = null;
433 if (existingGroup != null) {
434 existingID = existingGroup.getId();
436 PolicyLogger.error(MessageCodes.ERROR_DATA_ISSUE + " Group update had bad input. id=" + existingID +
437 " objectFromJSON=" + group);
438 loggingContext.transactionEnded();
439 PolicyLogger.audit("Transaction Failed - See Error.log");
440 response = "No Group";
443 // The Path on the PAP side is not carried on the RESTful interface with the AC
444 // (because it is local to the PAP)
445 // so we need to fill that in before submitting the group for update
446 ((StdPDPGroup) group).setDirectory(((StdPDPGroup) existingGroup).getDirectory());
448 acPutTransaction.updateGroup(group, "XACMLPapServlet.doDelete", null);
449 } catch (Exception e) {
450 PolicyLogger.error(MessageCodes.ERROR_PROCESS_FLOW, e, "XACMLPapServlet",
451 " Error while updating group in the database: "
452 + "group=" + existingGroup.getId());
453 response = "DB Error";
457 XACMLPapServlet.getPAPEngine().updateGroup(group);
458 } catch (PAPException e) {
459 PolicyLogger.error("Exception occured While Updating PDP Groups" + e);
460 response = "error in updateGroup method";
462 PolicyLogger.debug("Group '" + group.getId() + "' updated");
463 acPutTransaction.commitTransaction();
464 // Group changed, which might include changing the policies
466 newgroup = existingGroup;
467 } catch (Exception e) {
468 PolicyLogger.error("Exception occured in Group Change Method" + e);
469 response = "error in groupChanged method";
471 if (response == null) {
472 response = "success";
473 loggingContext.transactionEnded();
474 PolicyLogger.audit("Policy successfully deleted!");
476 loggingContext.transactionEnded();
477 PolicyLogger.audit("Transaction Ended");
481 public OnapPDPGroup getDeletedGroup() {
485 public boolean preSafetyCheck(PDPPolicy policy) {
489 public static DeleteHandler getInstance() {
491 Class<?> deleteHandler = Class.forName(
492 XACMLProperties.getProperty("deletePolicy.impl.className", DeleteHandler.class.getName()));
493 return (DeleteHandler) deleteHandler.newInstance();
494 } catch (Exception e) {
495 logger.error(e.getMessage(), e);