2 * ============LICENSE_START=======================================================
4 * ================================================================================
5 * Copyright (C) 2017 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=========================================================
21 package org.onap.policy.pap.xacml.rest.components;
23 import java.io.ByteArrayInputStream;
25 import java.io.FileInputStream;
26 import java.io.FileNotFoundException;
27 import java.io.FileWriter;
28 import java.io.IOException;
29 import java.io.InputStream;
30 import java.io.StringReader;
31 import java.net.HttpURLConnection;
32 import java.net.MalformedURLException;
33 import java.net.ProtocolException;
35 import java.nio.charset.StandardCharsets;
36 import java.nio.file.Files;
37 import java.nio.file.InvalidPathException;
38 import java.nio.file.Path;
39 import java.nio.file.Paths;
40 import java.security.Key;
41 import java.util.Base64;
42 import java.util.Date;
43 import java.util.HashMap;
44 import java.util.HashSet;
45 import java.util.Iterator;
46 import java.util.LinkedList;
47 import java.util.List;
50 import java.util.UUID;
52 import javax.crypto.Cipher;
53 import javax.crypto.spec.SecretKeySpec;
54 import javax.persistence.EntityManager;
55 import javax.persistence.EntityManagerFactory;
56 import javax.persistence.LockModeType;
57 import javax.persistence.PersistenceException;
58 import javax.persistence.Query;
59 import javax.persistence.RollbackException;
60 import javax.xml.parsers.DocumentBuilder;
61 import javax.xml.parsers.DocumentBuilderFactory;
62 import javax.xml.xpath.XPath;
63 import javax.xml.xpath.XPathFactory;
65 import org.apache.commons.io.FilenameUtils;
66 import org.apache.commons.io.IOUtils;
67 import org.onap.policy.common.logging.eelf.MessageCodes;
68 import org.onap.policy.common.logging.eelf.PolicyLogger;
69 import org.onap.policy.common.logging.flexlogger.FlexLogger;
70 import org.onap.policy.common.logging.flexlogger.Logger;
71 import org.onap.policy.pap.xacml.rest.XACMLPapServlet;
72 import org.onap.policy.rest.XACMLRestProperties;
73 import org.onap.policy.rest.adapter.PolicyRestAdapter;
74 import org.onap.policy.rest.jpa.ActionBodyEntity;
75 import org.onap.policy.rest.jpa.ConfigurationDataEntity;
76 import org.onap.policy.rest.jpa.DatabaseLockEntity;
77 import org.onap.policy.rest.jpa.GroupEntity;
78 import org.onap.policy.rest.jpa.PdpEntity;
79 import org.onap.policy.rest.jpa.PolicyDBDaoEntity;
80 import org.onap.policy.rest.jpa.PolicyEntity;
81 import org.onap.policy.rest.util.Webapps;
82 import org.onap.policy.xacml.api.pap.OnapPDP;
83 import org.onap.policy.xacml.api.pap.OnapPDPGroup;
84 import org.onap.policy.xacml.api.pap.PAPPolicyEngine;
85 import org.onap.policy.xacml.std.pap.StdPDPGroup;
86 import org.onap.policy.xacml.std.pap.StdPDPPolicy;
87 import org.onap.policy.xacml.util.XACMLPolicyWriter;
88 import org.w3c.dom.Document;
89 import org.xml.sax.InputSource;
91 import com.att.research.xacml.api.pap.PAPException;
92 import com.att.research.xacml.api.pap.PDP;
93 import com.att.research.xacml.api.pap.PDPPolicy;
94 import com.att.research.xacml.util.XACMLProperties;
96 import oasis.names.tc.xacml._3_0.core.schema.wd_17.PolicyType;
98 public class PolicyDBDao {
99 private static final Logger logger = FlexLogger.getLogger(PolicyDBDao.class);
100 private List<?> otherServers;
101 private EntityManagerFactory emf;
102 private static PolicyDBDao currentInstance = null;
103 private PAPPolicyEngine papEngine;
105 public static final String JSON_CONFIG = "JSON";
106 public static final String XML_CONFIG = "XML";
107 public static final String PROPERTIES_CONFIG = "PROPERTIES";
108 public static final String OTHER_CONFIG = "OTHER";
109 public static final String AUDIT_USER = "audit";
112 * Get an instance of a PolicyDBDao. It creates one if it does not exist.
113 * Only one instance is allowed to be created per server.
114 * @param emf The EntityFactoryManager to be used for database connections
115 * @return The new instance of PolicyDBDao or throw exception if the given emf is null.
116 * @throws IllegalStateException if a PolicyDBDao has already been constructed. Call getPolicyDBDaoInstance() to get this.
118 public static PolicyDBDao getPolicyDBDaoInstance(EntityManagerFactory emf) throws Exception{
119 logger.debug("getPolicyDBDaoInstance(EntityManagerFactory emf) as getPolicyDBDaoInstance("+emf+") called");
120 if(currentInstance == null){
122 currentInstance = new PolicyDBDao(emf);
123 return currentInstance;
125 throw new IllegalStateException("The EntityManagerFactory is Null");
127 return currentInstance;
131 * Gets the current instance of PolicyDBDao.
132 * @return The instance of PolicyDBDao or throws exception if the given instance is null.
133 * @throws IllegalStateException if a PolicyDBDao instance is null. Call createPolicyDBDaoInstance(EntityManagerFactory emf) to get this.
135 public static PolicyDBDao getPolicyDBDaoInstance() throws Exception{
136 logger.debug("getPolicyDBDaoInstance() as getPolicyDBDaoInstance() called");
137 if(currentInstance != null){
138 return currentInstance;
140 throw new IllegalStateException("The PolicyDBDao.currentInstance is Null. Use getPolicyDBDao(EntityManagerFactory emf)");
142 public void setPapEngine(PAPPolicyEngine papEngine2){
143 this.papEngine = (PAPPolicyEngine) papEngine2;
145 private PolicyDBDao(EntityManagerFactory emf){
146 logger.debug("PolicyDBDao(EntityManagerFactory emf) as PolicyDBDao("+emf+") called");
149 //not needed in this release
151 PolicyLogger.error("This server's PolicyDBDao instance could not be registered and may not reveive updates");
154 otherServers = getRemotePolicyDBDaoList();
155 if(logger.isDebugEnabled()){
156 logger.debug("Number of remote PolicyDBDao instances: "+otherServers.size());
158 if(otherServers.isEmpty()){
159 logger.warn("List of PolicyDBDao servers is empty or could not be retrieved");
163 //not static because we are going to be using the instance's emf
164 //waitTime in ms to wait for lock, or -1 to wait forever (no)
165 private void startTransactionSynced(EntityManager entityMgr,int waitTime){
166 logger.debug("\n\nstartTransactionSynced(EntityManager entityMgr,int waitTime) as "
167 + "\n startTransactionSynced("+entityMgr+","+waitTime+") called\n\n");
168 DatabaseLockEntity lock = null;
170 entityMgr.setProperty("javax.persistence.query.timeout", waitTime);
171 entityMgr.getTransaction().begin();
173 if(logger.isDebugEnabled()){
174 Map<String,Object> properties = entityMgr.getProperties();
175 logger.debug("\n\nstartTransactionSynced():"
176 + "\n entityManager.getProperties() = " + properties
180 if(logger.isDebugEnabled()){
181 logger.debug("\n\nstartTransactionSynced():"
182 + "\n ATTEMPT to get the DB lock"
185 lock = entityMgr.find(DatabaseLockEntity.class, 1, LockModeType.PESSIMISTIC_WRITE);
186 if(logger.isDebugEnabled()){
187 logger.debug("\n\nstartTransactionSynced():"
188 + "\n GOT the DB lock"
191 } catch(Exception e){
192 System.out.println("Could not get lock entity");
193 logger.error("Exception Occured"+e);
196 throw new IllegalStateException("The lock row does not exist in the table. Please create a primary key with value = 1.");
201 * Gets the list of other registered PolicyDBDaos from the database
202 * @return List (type PolicyDBDaoEntity) of other PolicyDBDaos
204 private List<?> getRemotePolicyDBDaoList(){
205 logger.debug("getRemotePolicyDBDaoList() as getRemotePolicyDBDaoList() called");
206 List<?> policyDBDaoEntityList = new LinkedList<>();
207 EntityManager em = emf.createEntityManager();
208 startTransactionSynced(em, 1000);
210 Query getPolicyDBDaoEntityQuery = em.createNamedQuery("PolicyDBDaoEntity.findAll");
211 policyDBDaoEntityList = getPolicyDBDaoEntityQuery.getResultList();
213 } catch(Exception e){
214 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Exception querying for other registered PolicyDBDaos");
215 logger.warn("List of remote PolicyDBDaos will be empty", e);
218 em.getTransaction().commit();
219 } catch(Exception e){
220 logger.warn("List of remote PolicyDBDaos will be empty", e);
222 em.getTransaction().rollback();
223 } catch(Exception e2){
224 logger.debug("List of remote PolicyDBDaos will be empty", e2);
228 return policyDBDaoEntityList;
231 public PolicyDBDaoTransaction getNewTransaction(){
232 logger.debug("getNewTransaction() as getNewTransaction() called");
233 return (PolicyDBDaoTransaction)(new PolicyDBDaoTransactionInstance());
237 * Because the normal transactions are not used in audits, we can use the same transaction
238 * mechanism to get a transaction and obtain the emlock and the DB lock. We just need to
239 * provide different transaction timeout values in ms because the audit will run longer
240 * than normal transactions.
242 public PolicyDBDaoTransaction getNewAuditTransaction(){
243 logger.debug("getNewAuditTransaction() as getNewAuditTransaction() called");
244 //Use the standard transaction wait time in ms
245 int auditWaitMs = Integer.parseInt(XACMLProperties.getProperty(XACMLRestProperties.PROP_PAP_TRANS_WAIT));
246 //Use the (extended) audit timeout time in ms
247 int auditTimeoutMs = Integer.parseInt(XACMLProperties.getProperty(XACMLRestProperties.PROP_PAP_AUDIT_TIMEOUT));
248 return (PolicyDBDaoTransaction)(new PolicyDBDaoTransactionInstance(auditTimeoutMs, auditWaitMs));
253 * Checks if two strings are equal. Null strings ARE allowed.
254 * @param one A String or null to compare
255 * @param two A String or null to compare
257 private static boolean stringEquals(String one, String two){
258 logger.debug("stringEquals(String one, String two) as stringEquals("+one+", "+two+") called");
259 if(one == null && two == null){
262 if(one == null || two == null){
265 return one.equals(two);
269 * Computes the scope in dotted format based on an absolute path and a path that divides the scope.
270 * @param fullPath An absolute path including scope folders and other folders(does not have to be absolute, must just contain scope and other folders before)
271 * @param pathToExclude The path that acts as a division between the scope and the other folders
272 * @return The scope in dotted format (org.onap)
274 private static String computeScope(String fullPath, String pathToExclude){
275 logger.debug("computeScope(String fullPath, String pathToExclude) as computeScope("+fullPath+", "+pathToExclude+") called");
276 int excludeIndex = fullPath.indexOf(pathToExclude);
277 String scopePath = fullPath.substring(excludeIndex+pathToExclude.length());
278 String scope = scopePath.replace('\\', '.');
279 scope = scope.replace('/', '.');
280 if(scope.charAt(0) == '.'){
281 scope = scope.substring(1);
283 if(scope.charAt(scope.length()-1) == '.'){
284 scope = scope.substring(0, scope.length()-1);
290 * Returns the url of this local pap server, removing the username and password, if they are present
291 * @return The url of this local pap server
293 private String[] getPapUrlUserPass(){
294 logger.debug("getPapUrl() as getPapUrl() called");
295 String url = XACMLProperties.getProperty(XACMLRestProperties.PROP_PAP_URL);
299 return splitPapUrlUserPass(url);
303 private String[] splitPapUrlUserPass(String url){
304 String[] urlUserPass = new String[3];
305 String[] commaSplit = url.split(",");
306 urlUserPass[0] = commaSplit[0];
307 if(commaSplit.length > 2){
308 urlUserPass[1] = commaSplit[1];
309 urlUserPass[2] = commaSplit[2];
311 if(urlUserPass[1] == null || urlUserPass[1].equals("")){
312 String usernamePropertyValue = XACMLProperties.getProperty(XACMLRestProperties.PROP_PAP_USERID);
313 if(usernamePropertyValue != null){
314 urlUserPass[1] = usernamePropertyValue;
317 if(urlUserPass[2] == null || urlUserPass[2].equals("")){
318 String passwordPropertyValue = XACMLProperties.getProperty(XACMLRestProperties.PROP_PAP_PASS);
319 if(passwordPropertyValue != null){
320 urlUserPass[2] = passwordPropertyValue;
323 //if there is no comma, for some reason there is no username and password, so don't try to cut them off
327 private static String encryptPassword(String password) throws Exception{
328 Cipher cipher = Cipher.getInstance("AES");
329 cipher.init(Cipher.ENCRYPT_MODE, aesKey());
330 byte[] encryption = cipher.doFinal(password.getBytes("UTF-8"));
331 System.out.println(encryption);
332 return new String(Base64.getMimeEncoder().encode(encryption),"UTF-8");
335 private static String decryptPassword(String encryptedPassword) throws Exception{
336 Cipher cipher = Cipher.getInstance("AES");
337 cipher.init(Cipher.DECRYPT_MODE, aesKey());
338 byte[] password = cipher.doFinal(Base64.getDecoder().decode(encryptedPassword.getBytes("UTF-8")));
339 return new String(password,"UTF-8");
341 private static Key aesKey(){
342 byte[] aesValue = (new String("njrmbklcxtoplawf")).getBytes();
343 return new SecretKeySpec(aesValue,"AES");
346 * Register the PolicyDBDao instance in the PolicyDBDaoEntity table
347 * @return Boolean, were we able to register?
349 private boolean register(){
350 logger.debug("register() as register() called");
351 String[] url = getPapUrlUserPass();
352 EntityManager em = emf.createEntityManager();
354 startTransactionSynced(em, 1000);
355 } catch(IllegalStateException e){
356 logger.debug ("\nPolicyDBDao.register() caught an IllegalStateException: \n" +e + "\n");
357 DatabaseLockEntity lock;
358 lock = em.find(DatabaseLockEntity.class, 1);
360 lock = new DatabaseLockEntity();
365 em.getTransaction().commit();
367 } catch(Exception e2){
368 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e2, "PolicyDBDao", "COULD NOT CREATE DATABASELOCK ROW. WILL TRY ONE MORE TIME");
371 em = emf.createEntityManager();
373 startTransactionSynced(em, 1000);
374 } catch(Exception e3){
375 String msg = "DATABASE LOCKING NOT WORKING. CONCURRENCY CONTROL NOT WORKING";
376 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e3, "PolicyDBDao", msg);
377 throw new IllegalStateException("msg" + "\n" + e3);
381 logger.debug("\nPolicyDBDao.register. Database locking and concurrency control is initialized\n");
382 PolicyDBDaoEntity foundPolicyDBDaoEntity = em.find(PolicyDBDaoEntity.class, url[0]);
383 Query getPolicyDBDaoEntityQuery = em.createQuery("SELECT e FROM PolicyDBDaoEntity e WHERE e.policyDBDaoUrl=:url");
384 getPolicyDBDaoEntityQuery.setParameter("url", url[0]);
385 if(foundPolicyDBDaoEntity == null){
386 PolicyDBDaoEntity newPolicyDBDaoEntity = new PolicyDBDaoEntity();
387 em.persist(newPolicyDBDaoEntity);
388 newPolicyDBDaoEntity.setPolicyDBDaoUrl(url[0]);
389 newPolicyDBDaoEntity.setDescription("PAP server at "+url[0]);
390 newPolicyDBDaoEntity.setUsername(url[1]);
392 newPolicyDBDaoEntity.setPassword(encryptPassword(url[2]));
393 } catch(Exception e){
395 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Could not encrypt PAP password");
398 em.getTransaction().commit();
399 } catch(Exception e){
402 em.getTransaction().rollback();
403 } catch(Exception e2){
405 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e2, "PolicyDBDao", "Could not add new PolicyDBDao to the database");
409 //just want to update in order to change modified date
410 String encryptedPassword = null;
412 encryptedPassword = encryptPassword(url[2]);
413 } catch(Exception e){
415 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Could not encrypt PAP password");
417 if(url[1] != null && !stringEquals(url[1], foundPolicyDBDaoEntity.getUsername())){
418 foundPolicyDBDaoEntity.setUsername(url[1]);
420 if(encryptedPassword != null && !stringEquals(encryptedPassword, foundPolicyDBDaoEntity.getPassword())){
421 foundPolicyDBDaoEntity.setPassword(encryptedPassword);
423 foundPolicyDBDaoEntity.preUpdate();
425 em.getTransaction().commit();
426 } catch(Exception e){
429 em.getTransaction().rollback();
430 } catch(Exception e2){
432 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e2, "PolicyDBDao", "Could not update PolicyDBDao in the database");
437 logger.debug("\nPolicyDBDao.register(). Success!!\n");
440 public void notifyOthers(long entityId,String entityType){
441 notifyOthers(entityId,entityType,null);
443 public void notifyOthers(long entityId, String entityType, String newGroupId){
444 logger.debug("notifyOthers(long entityId, String entityType, long newGroupId) as notifyOthers("+entityId+","+entityType+","+newGroupId+") called");
445 LinkedList<Thread> notifyThreads = new LinkedList<>();
447 //we're going to run notifications in parallel threads to speed things up
448 for(Object obj : otherServers){
450 Thread newNotifyThread = new Thread(new NotifyOtherThread(obj, entityId, entityType, newGroupId));
452 newNotifyThread.start();
454 notifyThreads.add(newNotifyThread);
457 //we want to wait for all notifications to complete or timeout before we unlock the interface and allow more changes
458 for(Thread t : notifyThreads){
461 } catch (Exception e) {
462 logger.warn("Could not join a notifcation thread" + e);
469 private class NotifyOtherThread implements Runnable {
470 public NotifyOtherThread(Object obj, long entityId, String entityType, String newGroupId){
472 this.entityId = entityId;
473 this.entityType = entityType;
474 this.newGroupId = newGroupId;
477 private long entityId;
478 private String entityType;
479 private String newGroupId;
482 //naming of 'o' is for backwards compatibility with the rest of the function
483 PolicyDBDaoEntity dbdEntity = (PolicyDBDaoEntity)obj;
484 String o = dbdEntity.getPolicyDBDaoUrl();
485 String username = dbdEntity.getUsername();
488 password = decryptPassword(dbdEntity.getPassword());
489 } catch(Exception e){
491 //if we can't decrypt, might as well try it anyway
492 password = dbdEntity.getPassword();
494 Base64.Encoder encoder = Base64.getEncoder();
495 String encoding = encoder.encodeToString((username+":"+password).getBytes(StandardCharsets.UTF_8));
496 HttpURLConnection connection = null;
497 UUID requestID = UUID.randomUUID();
500 String papUrl = getPapUrlUserPass()[0];
502 papUrl = "undefined";
504 logger.debug("We are going to try to notify "+o);
505 //is this our own url?
508 ourUrl = splitPapUrlUserPass((String)o)[0];
516 if(papUrl.equals(ourUrl)){
517 logger.debug(((String)o)+" is our url, skipping notify");
520 if(newGroupId == null){
521 url = new URL(((String)o)+"?policydbdaourl="+papUrl+"&entityid="+entityId+"&entitytype="+entityType);
523 url = new URL(((String)o)+"?policydbdaourl="+papUrl+"&entityid="+entityId+"&entitytype="+entityType+"&extradata="+newGroupId);
525 } catch (MalformedURLException e) {
526 logger.warn("Caught MalformedURLException on: new URL()", e);
530 // Open up the connection
532 logger.debug("Connecting with url: "+url);
534 connection = (HttpURLConnection)url.openConnection();
535 } catch (Exception e) {
536 logger.warn("Caught exception on: url.openConnection()",e);
540 // Setup our method and headers
543 connection.setRequestMethod("PUT");
544 } catch (ProtocolException e) {
545 //why would this error ever occur?
546 logger.warn("Caught ProtocolException on connection.setRequestMethod(\"PUT\");",e);
549 connection.setRequestProperty("Authorization", "Basic " + encoding);
550 connection.setRequestProperty("Accept", "text/x-java-properties");
551 connection.setRequestProperty("Content-Type", "text/x-java-properties");
552 connection.setRequestProperty("requestID", requestID.toString());
555 readTimeout = Integer.parseInt(XACMLProperties.getProperty(XACMLRestProperties.PROP_PAP_NOTIFY_TIMEOUT));
557 } catch(Exception e){
558 logger.error("xacml.rest.pap.notify.timeoutms property not set, using a default.", e);
561 connection.setReadTimeout(readTimeout);
562 connection.setConnectTimeout(readTimeout);
563 connection.setUseCaches(false);
565 // Adding this in. It seems the HttpUrlConnection class does NOT
566 // properly forward our headers for POST re-direction. It does so
567 // for a GET re-direction.
569 // So we need to handle this ourselves.
571 connection.setInstanceFollowRedirects(false);
572 connection.setDoOutput(true);
573 connection.setDoInput(true);
575 connection.connect();
576 } catch (Exception e) {
577 logger.warn("Caught exception on: connection.connect()",e);
581 if (connection.getResponseCode() == 200) {
582 logger.info("Received response 200 from pap server on notify");
585 logger.warn("connection response code not 200, received: "+connection.getResponseCode());
587 } catch (Exception e) {
588 logger.warn("Caught Exception on: connection.getResponseCode() ", e);
592 connection.disconnect();
596 private static String evaluateXPath(String expression, String xml) {
597 InputSource source = new InputSource(new StringReader(xml));
599 DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
600 String description = "";
602 DocumentBuilder db = dbf.newDocumentBuilder();
603 Document document = db.parse(source);
605 XPathFactory xpathFactory = XPathFactory.newInstance();
606 XPath xpath = xpathFactory.newXPath();
609 description = xpath.evaluate(expression, document);
611 logger.error("Exception Occured while evaluating path"+e);
617 private static String getDescriptionFromXacml(String xacmlData){
618 String openTag = "<Description>";
619 String closeTag = "</Description>";
620 int descIndex = xacmlData.indexOf(openTag);
621 int endDescIndex = xacmlData.indexOf(closeTag);
622 String desc = xacmlData.substring(descIndex+openTag.length(),endDescIndex);
626 private final String POLICY_NOTIFICATION = "policy";
627 private final String PDP_NOTIFICATION = "pdp";
628 private final String GROUP_NOTIFICATION = "group";
629 public void handleIncomingHttpNotification(String url, String entityId, String entityType, String extraData, XACMLPapServlet xacmlPapServlet){
630 logger.info("DBDao url: " + url + " has reported an update on "+entityType+" entity "+entityId);
631 PolicyDBDaoTransaction transaction = this.getNewTransaction();
632 //although its named retries, this is the total number of tries
635 retries = Integer.parseInt(XACMLProperties.getProperty(XACMLRestProperties.PROP_PAP_INCOMINGNOTIFICATION_TRIES));
637 } catch(Exception e){
638 logger.error("xacml.rest.pap.incomingnotification.tries property not set, using a default of 3."+e);
641 //if someone sets it to some dumb value, we need to make sure it will try at least once
645 int pauseBetweenRetries = 1000;
648 case POLICY_NOTIFICATION:
649 for(int i=0; i<retries;i++){
651 handleIncomingPolicyChange(url, entityId,extraData);
653 } catch(Exception e){
655 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught exception on handleIncomingPolicyChange("+url+", "+entityId+", "+extraData+")");
658 Thread.sleep(pauseBetweenRetries);
659 }catch(InterruptedException ie){
660 Thread.currentThread().interrupt();
665 case PDP_NOTIFICATION:
666 for(int i=0; i<retries;i++){
668 handleIncomingPdpChange(url, entityId, transaction);
670 } catch(Exception e){
672 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught exception on handleIncomingPdpChange("+url+", "+entityId+", "+transaction+")");
675 Thread.sleep(pauseBetweenRetries);
676 }catch(InterruptedException ie){
677 Thread.currentThread().interrupt();
682 case GROUP_NOTIFICATION:
683 for(int i=0; i<retries;i++){
685 handleIncomingGroupChange(url, entityId, extraData, transaction, xacmlPapServlet);
689 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught exception on handleIncomingGroupChange("+url+", "+entityId+", "+extraData+", "+transaction+", "+xacmlPapServlet+")");
692 Thread.sleep(pauseBetweenRetries);
693 }catch(InterruptedException ie){
694 Thread.currentThread().interrupt();
700 //no changes should be being made in this function, we still need to close
701 transaction.rollbackTransaction();
703 private void handleIncomingGroupChange(String url, String groupId, String extraData,PolicyDBDaoTransaction transaction,XACMLPapServlet xacmlPapServlet) throws PAPException{
704 GroupEntity groupRecord = null;
705 long groupIdLong = -1;
707 groupIdLong = Long.parseLong(groupId);
708 } catch(NumberFormatException e){
709 throw new IllegalArgumentException("groupId "+groupId+" cannot be parsed into a long");
712 groupRecord = transaction.getGroup(groupIdLong);
713 } catch(Exception e){
714 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught Exception trying to get pdp group record with transaction.getGroup("+groupIdLong+");");
715 throw new PAPException("Could not get local group "+groupIdLong);
717 if(groupRecord == null){
718 throw new PersistenceException("The group record returned is null");
720 //compare to local fs
721 //does group folder exist
722 OnapPDPGroup localGroup = null;
724 localGroup = papEngine.getGroup(groupRecord.getGroupId());
725 } catch (Exception e) {
726 logger.warn("Caught PAPException trying to get local pdp group with papEngine.getGroup("+groupId+");",e);
728 if(localGroup == null && extraData != null){
729 //here we can try to load an old group id from the extraData
731 localGroup = papEngine.getGroup(extraData);
733 logger.warn("Caught PAPException trying to get local pdp group with papEngine.getGroup("+extraData+");",e);
736 if(localGroup != null && groupRecord.isDeleted()){
737 OnapPDPGroup newLocalGroup = null;
738 if(extraData != null){
740 newLocalGroup = papEngine.getGroup(extraData);
741 } catch (PAPException e) {
742 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught PAPException trying to get new pdp group with papEngine.getGroup("+extraData+");");
746 papEngine.removeGroup(localGroup, newLocalGroup);
747 } catch (NullPointerException | PAPException e) {
748 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught PAPException trying to get remove pdp group with papEngine.removeGroup("+localGroup+", "+newLocalGroup+");");
749 throw new PAPException("Could not remove group "+groupId);
752 else if(localGroup == null){
753 //creating a new group
755 papEngine.newGroup(groupRecord.getgroupName(), groupRecord.getDescription());
756 } catch (NullPointerException | PAPException e) {
757 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught PAPException trying to create pdp group with papEngine.newGroup(groupRecord.getgroupName(), groupRecord.getDescription());");
758 throw new PAPException("Could not create group "+groupRecord);
761 localGroup = papEngine.getGroup(groupRecord.getGroupId());
762 } catch (PAPException e1) {
763 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e1, "PolicyDBDao", "Caught PAPException trying to get pdp group we just created with papEngine.getGroup(groupRecord.getGroupId());\nAny PDPs or policies in the new group may not have been added");
766 //add possible pdps to group
767 List<?> pdpsInGroup = transaction.getPdpsInGroup(Long.parseLong(groupRecord.getGroupId()));
768 for(Object pdpO : pdpsInGroup){
769 PdpEntity pdp = (PdpEntity)pdpO;
771 papEngine.newPDP(pdp.getPdpId(), localGroup, pdp.getPdpName(), pdp.getDescription(), pdp.getJmxPort());
772 } catch (NullPointerException | PAPException e) {
773 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught PAPException trying to get create pdp with papEngine.newPDP(pdp.getPdpId(), localGroup, pdp.getPdpName(), pdp.getDescription(), pdp.getJmxPort());");
774 throw new PAPException("Could not create pdp "+pdp);
777 //add possible policies to group (filesystem only, apparently)
779 if(!(localGroup instanceof StdPDPGroup)){
780 throw new PAPException("group is not a StdPDPGroup");
783 //because it will be comparing the new group to its own version
784 StdPDPGroup localGroupClone = new StdPDPGroup(localGroup.getId(),localGroup.isDefaultGroup(),localGroup.getName(),localGroup.getDescription(),((StdPDPGroup)localGroup).getDirectory());
785 localGroupClone.setOnapPdps(localGroup.getOnapPdps());
786 localGroupClone.setPipConfigs(localGroup.getPipConfigs());
787 localGroupClone.setStatus(localGroup.getStatus());
788 //we are updating a group or adding a policy or changing default
789 //set default if it should be
790 if(!localGroupClone.isDefaultGroup() && groupRecord.isDefaultGroup()){
792 papEngine.SetDefaultGroup(localGroup);
794 } catch (PAPException e) {
795 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught PAPException trying to set default group with papEngine.SetDefaultGroup("+localGroupClone+");");
796 throw new PAPException("Could not set default group to "+localGroupClone);
799 boolean needToUpdate = false;
800 if(updateGroupPoliciesInFileSystem(localGroupClone,localGroup, groupRecord, transaction)){
803 if(!stringEquals(localGroupClone.getId(),groupRecord.getGroupId()) || !stringEquals(localGroupClone.getName(),groupRecord.getgroupName())){
805 //we do not want to change the id, the papEngine will do this for us, it needs to know the old id
806 localGroupClone.setName(groupRecord.getgroupName());
809 if(!stringEquals(localGroupClone.getDescription(),groupRecord.getDescription())){
810 localGroupClone.setDescription(groupRecord.getDescription());
816 papEngine.updateGroup(localGroupClone);
817 } catch (PAPException e) {
818 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught PAPException trying to update group with papEngine.updateGroup("+localGroupClone+");");
819 throw new PAPException("Could not update group "+localGroupClone);
824 //call command that corresponds to the change that was made
826 //this will also handle removes, since incoming pdpGroup has no policies internally, we are just going to add them all in from the db
827 private boolean updateGroupPoliciesInFileSystem(OnapPDPGroup pdpGroup,OnapPDPGroup oldPdpGroup, GroupEntity groupRecord, PolicyDBDaoTransaction transaction) throws PAPException{
828 if(!(pdpGroup instanceof StdPDPGroup)){
829 throw new PAPException("group is not a StdPDPGroup");
831 StdPDPGroup group = (StdPDPGroup)pdpGroup;
832 //this must always be true since we don't explicitly know when a delete is occuring
833 boolean didUpdate = true;
834 HashMap<String,PDPPolicy> currentPolicySet = new HashMap<String,PDPPolicy>(oldPdpGroup.getPolicies().size());
835 HashSet<PDPPolicy> newPolicySet = new HashSet<>();
836 for(PDPPolicy pdpPolicy : oldPdpGroup.getPolicies()){
837 currentPolicySet.put(pdpPolicy.getId(), pdpPolicy);
839 for(PolicyEntity policy : groupRecord.getPolicies()){
840 String pdpPolicyName = getPdpPolicyName(policy.getPolicyName(), policy.getScope());
841 if(group.getPolicy(pdpPolicyName) == null){
843 if(currentPolicySet.containsKey(pdpPolicyName)){
844 newPolicySet.add(currentPolicySet.get(pdpPolicyName));
846 InputStream policyStream = new ByteArrayInputStream(policy.getPolicyData().getBytes());
847 group.copyPolicyToFile(pdpPolicyName,policyStream);
848 ((StdPDPPolicy)(group.getPolicy(pdpPolicyName))).setName(removeExtensionAndVersionFromPolicyName(policy.getPolicyName()));
850 policyStream.close();
851 } catch (IOException e) {
853 PolicyLogger.error(e.getMessage() +e);
859 newPolicySet.addAll(group.getPolicies());
860 group.setPolicies(newPolicySet);
865 private String removeExtensionAndVersionFromPolicyName(String originalPolicyName){
866 return getPolicyNameAndVersionFromPolicyFileName(originalPolicyName)[0];
870 * Splits apart the policy name and version from a policy file path
871 * @param originalPolicyName: a policy file name ex: Config_policy.2.xml
872 * @return An array [0]: The policy name, [1]: the policy version, as a string
874 private String[] getPolicyNameAndVersionFromPolicyFileName(String originalPolicyName){
875 String policyName = originalPolicyName;
876 String[] nameAndVersion = new String[2];
878 policyName = removeFileExtension(policyName);
879 nameAndVersion[0] = policyName.substring(0,policyName.lastIndexOf('.'));
880 if(isNullOrEmpty(nameAndVersion[0])){
881 throw new Exception();
883 } catch(Exception e){
884 nameAndVersion[0] = originalPolicyName;
888 nameAndVersion[1] = policyName.substring(policyName.lastIndexOf('.')+1);
889 if(isNullOrEmpty(nameAndVersion[1])){
890 throw new Exception();
892 } catch(Exception e){
893 nameAndVersion[1] = "1";
896 return nameAndVersion;
899 private void handleIncomingPdpChange(String url, String pdpId, PolicyDBDaoTransaction transaction) throws PAPException{
903 pdpIdLong = Long.parseLong(pdpId);
904 }catch(NumberFormatException e){
905 throw new IllegalArgumentException("pdpId "+pdpId+" cannot be parsed into a long");
907 PdpEntity pdpRecord = null;
909 pdpRecord = transaction.getPdp(pdpIdLong);
911 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught Exception trying to get pdp record with transaction.getPdp("+pdpIdLong+");");
912 throw new PAPException("Could not get local pdp "+pdpIdLong);
914 if(pdpRecord == null){
915 throw new PersistenceException("The pdpRecord returned is null");
919 localPdp = papEngine.getPDP(pdpRecord.getPdpId());
920 } catch (PAPException e) {
921 logger.warn("Caught PAPException trying to get local pdp with papEngine.getPDP("+pdpId+");",e);
923 if(localPdp != null && pdpRecord.isDeleted()){
925 papEngine.removePDP((OnapPDP) localPdp);
926 } catch (PAPException e) {
927 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught PAPException trying to get remove pdp with papEngine.removePDP("+localPdp+");");
928 throw new PAPException("Could not remove pdp "+pdpId);
931 else if(localPdp == null){
934 OnapPDPGroup localGroup = null;
936 localGroup = papEngine.getGroup(pdpRecord.getGroup().getGroupId());
937 } catch (PAPException e1) {
938 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e1, "PolicyDBDao", "Caught PAPException trying to get local group to add pdp to with papEngine.getGroup(pdpRecord.getGroup().getGroupId());");
939 throw new PAPException("Could not get local group");
942 papEngine.newPDP(pdpRecord.getPdpId(), localGroup, pdpRecord.getPdpName(), pdpRecord.getDescription(), pdpRecord.getJmxPort());
943 } catch (NullPointerException | PAPException e) {
944 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught PAPException trying to create pdp with papEngine.newPDP("+pdpRecord.getPdpId()+", "+localGroup+", "+pdpRecord.getPdpName()+", "+pdpRecord.getDescription()+", "+pdpRecord.getJmxPort()+");");
945 throw new PAPException("Could not create pdp "+pdpRecord);
948 boolean needToUpdate = false;
949 if(!stringEquals(localPdp.getId(),pdpRecord.getPdpId()) || !stringEquals(localPdp.getName(),pdpRecord.getPdpName())){
950 //again, we don't want to change the id, the papEngine will do this
951 localPdp.setName(pdpRecord.getPdpName());
954 if(!stringEquals(localPdp.getDescription(),pdpRecord.getDescription())){
955 localPdp.setDescription(pdpRecord.getDescription());
958 String localPdpGroupId = null;
960 localPdpGroupId = papEngine.getPDPGroup((OnapPDP) localPdp).getId();
961 } catch(PAPException e){
962 //could be null or something, just warn at this point
963 logger.warn("Caught PAPException trying to get id of local group that pdp is in with localPdpGroupId = papEngine.getPDPGroup(localPdp).getId();",e);
965 if(!stringEquals(localPdpGroupId,pdpRecord.getGroup().getGroupId())){
966 OnapPDPGroup newPdpGroup = null;
968 newPdpGroup = papEngine.getGroup(pdpRecord.getGroup().getGroupId());
969 }catch(PAPException e){
970 //ok, now we have an issue. Time to stop things
971 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught PAPException trying to get id of local group to move pdp to with papEngine.getGroup(pdpRecord.getGroup().getGroupId());");
972 throw new PAPException("Could not get local group");
975 papEngine.movePDP((OnapPDP) localPdp, newPdpGroup);
976 }catch(PAPException e){
977 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught PAPException trying to move pdp with papEngine.movePDP(localPdp, newPdpGroup);");
978 throw new PAPException("Could not move pdp "+localPdp);
981 if(((PdpEntity) localPdp).getJmxPort() != pdpRecord.getJmxPort()){
982 ((PdpEntity) localPdp).setJmxPort(pdpRecord.getJmxPort());
987 papEngine.updatePDP((OnapPDP) localPdp);
988 } catch (PAPException e) {
989 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught PAPException trying to update pdp with papEngine.updatePdp("+localPdp+");");
990 throw new PAPException("Could not update pdp "+localPdp);
994 //compare to local situation
995 //call command to update
997 private void handleIncomingPolicyChange(String url, String policyId,String oldPathString){
998 String policyName = null;
999 EntityManager em = emf.createEntityManager();
1000 Query getPolicyEntityQuery = em.createNamedQuery("PolicyEntity.FindById");
1001 getPolicyEntityQuery.setParameter("id", Long.valueOf(policyId));
1003 @SuppressWarnings("unchecked")
1004 List<PolicyEntity> policies = getPolicyEntityQuery.getResultList();
1005 PolicyEntity policy = null;
1006 if (!policies.isEmpty()){
1007 policy = policies.get(0);
1009 String action = "unknown action";
1012 policyName = policy.getPolicyName();
1013 logger.debug("Deleting Policy: " + policy.getPolicyName());
1015 Path subFile = null;
1017 if (policy.getConfigurationData()!= null){
1018 subFile = getPolicySubFile(policy.getConfigurationData().getConfigurationName(), "Config");
1019 }else if(policy.getActionBodyEntity()!= null){
1020 subFile = getPolicySubFile(policy.getActionBodyEntity().getActionBodyName(), "Action");
1023 if(subFile != null){
1024 Files.deleteIfExists(subFile);
1026 if (policy.getConfigurationData()!= null){
1027 writePolicySubFile(policy, "Config");
1028 }else if(policy.getActionBodyEntity()!= null){
1029 writePolicySubFile(policy, "Action");
1032 } catch (IOException e1) {
1033 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e1, "PolicyDBDao", "Error occurred while performing [" + action + "] of Policy File: " + policyName);
1037 private String getPdpPolicyName(String name, String scope){
1038 String finalName = "";
1041 finalName += removeFileExtension(name);
1042 finalName += ".xml";
1045 private String removeFileExtension(String fileName){
1046 return fileName.substring(0, fileName.lastIndexOf('.'));
1049 private Path getPolicySubFile(String filename, String subFileType){
1050 logger.debug("getPolicySubFile(" + filename + ", " + subFileType + ")");
1051 Path filePath = Paths.get(XACMLProperties.getProperty(XACMLRestProperties.PROP_PAP_WEBAPPS).toString(), subFileType);
1054 filename = FilenameUtils.removeExtension(filename);
1056 for(File tmpFile : filePath.toFile().listFiles()){
1057 if (FilenameUtils.removeExtension(tmpFile.getName()).equals(filename)){
1062 Path finalPath = null;
1064 finalPath = Paths.get(file.getAbsolutePath());
1067 logger.debug("end of getPolicySubFile: " + finalPath);
1071 private boolean writePolicySubFile(PolicyEntity policy, String policyType){
1072 logger.info("writePolicySubFile with policyName[" + policy.getPolicyName() + "] and policyType[" + policyType + "]");
1074 String subTypeName = null;
1075 String subTypeBody = null;
1076 if (policyType.equalsIgnoreCase("config")){
1078 subTypeName = FilenameUtils.removeExtension(policy.getConfigurationData().getConfigurationName());
1079 subTypeBody = policy.getConfigurationData().getConfigBody();
1081 String configType = policy.getConfigurationData().getConfigType();
1084 if (configType != null) {
1085 if (configType.equals(JSON_CONFIG)) {
1086 subTypeName = subTypeName + ".json";
1088 if (configType.equals(XML_CONFIG)) {
1089 subTypeName = subTypeName + ".xml";
1091 if (configType.equals(PROPERTIES_CONFIG)) {
1092 subTypeName = subTypeName + ".properties";
1094 if (configType.equals(OTHER_CONFIG)) {
1095 subTypeName = subTypeName + ".txt";
1099 }else if (policyType.equalsIgnoreCase("action")){
1101 subTypeName = policy.getActionBodyEntity().getActionBodyName();
1102 subTypeBody = policy.getActionBodyEntity().getActionBody();
1106 Path filePath = Paths.get(XACMLProperties.getProperty(XACMLRestProperties.PROP_PAP_WEBAPPS).toString(), type);
1108 if(subTypeBody == null){
1111 boolean success = false;
1113 Files.deleteIfExists(Paths.get(filePath.toString(), subTypeName));
1114 File file = Paths.get(filePath.toString(),subTypeName).toFile();
1115 file.createNewFile();
1116 FileWriter fileWriter = new FileWriter(file, false); // false to overwrite
1117 fileWriter.write(subTypeBody);
1121 } catch (Exception e) {
1122 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Exception occured while creating Configuration File for Policy : " + policy.getPolicyName());
1129 public void auditLocalDatabase(PAPPolicyEngine papEngine2){
1130 logger.debug("PolicyDBDao.auditLocalDatabase() is called");
1132 deleteAllGroupTables();
1133 auditGroups(papEngine2);
1134 } catch(Exception e){
1135 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "auditLocalDatabase() error");
1136 logger.error("Exception Occured"+e);
1140 public void deleteAllGroupTables(){
1141 logger.debug("PolicyDBDao.deleteAllGroupTables() called");
1142 EntityManager em = emf.createEntityManager();
1143 em.getTransaction().begin();
1145 Query deletePdpEntityEntityTableUpdate = em.createNamedQuery("PdpEntity.deleteAll");
1146 deletePdpEntityEntityTableUpdate.executeUpdate();
1148 Query deleteGroupEntityTableUpdate = em.createNamedQuery("GroupEntity.deleteAll");
1149 deleteGroupEntityTableUpdate.executeUpdate();
1151 em.getTransaction().commit();
1155 @SuppressWarnings("unchecked")
1156 public void auditGroups(PAPPolicyEngine papEngine2){
1157 logger.debug("PolicyDBDao.auditGroups() called");
1159 EntityManager em = emf.createEntityManager();
1160 em.getTransaction().begin();
1161 final String AUDIT_STR = "Audit";
1164 Set<OnapPDPGroup> groups = papEngine2.getOnapPDPGroups();
1166 for (OnapPDPGroup grp : groups){
1168 GroupEntity groupEntity = new GroupEntity();
1169 em.persist(groupEntity);
1170 groupEntity.setGroupName(grp.getName());
1171 groupEntity.setDescription(grp.getDescription());
1172 groupEntity.setDefaultGroup(grp.isDefaultGroup());
1173 groupEntity.setCreatedBy(AUDIT_STR);
1174 groupEntity.setGroupId(createNewPDPGroupId(grp.getId()));
1175 groupEntity.setModifiedBy(AUDIT_STR);
1176 Set<OnapPDP> pdps = grp.getOnapPdps();
1178 for(OnapPDP pdp : pdps){
1179 PdpEntity pdpEntity = new PdpEntity();
1180 em.persist(pdpEntity);
1181 pdpEntity.setGroup(groupEntity);
1182 pdpEntity.setJmxPort(pdp.getJmxPort());
1183 pdpEntity.setPdpId(pdp.getId());
1184 pdpEntity.setPdpName(pdp.getName());
1185 pdpEntity.setModifiedBy(AUDIT_STR);
1186 pdpEntity.setCreatedBy(AUDIT_STR);
1190 Set<PDPPolicy> policies = grp.getPolicies();
1192 for(PDPPolicy policy : policies){
1194 String[] stringArray = getNameScopeAndVersionFromPdpPolicy(policy.getId());
1195 List<PolicyEntity> policyEntityList;
1196 Query getPolicyEntitiesQuery = em.createNamedQuery("PolicyEntity.findByNameAndScope");
1197 getPolicyEntitiesQuery.setParameter("name", stringArray[0]);
1198 getPolicyEntitiesQuery.setParameter("scope", stringArray[1]);
1200 policyEntityList = getPolicyEntitiesQuery.getResultList();
1201 PolicyEntity policyEntity = null;
1202 if(!policyEntityList.isEmpty()){
1203 policyEntity = policyEntityList.get(0);
1205 if(policyEntity != null){
1206 groupEntity.addPolicyToGroup(policyEntity);
1208 }catch(Exception e2){
1209 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e2, "PolicyDBDao", "Exception auditGroups inner catch");
1212 }catch(Exception e1){
1213 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e1, "PolicyDBDao", "Exception auditGroups middle catch");
1216 }catch(Exception e){
1217 em.getTransaction().rollback();
1218 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Exception auditGroups outer catch");
1223 em.getTransaction().commit();
1228 private String getConfigFile(String filename, PolicyRestAdapter policy){
1230 return getConfigFile(filename, (String)null);
1232 return getConfigFile(filename, policy.getConfigType());
1234 //copied from ConfigPolicy.java and modified
1235 // Here we are adding the extension for the configurations file based on the
1236 // config type selection for saving.
1237 private String getConfigFile(String filename, String configType) {
1238 logger.debug("getConfigFile(String filename, String scope, String configType) as getConfigFile("+filename+", "+configType+") called");
1239 filename = FilenameUtils.removeExtension(filename);
1240 String id = configType;
1243 if (id.equals(ConfigPolicy.JSON_CONFIG) || id.contains("Firewall")) {
1244 filename = filename + ".json";
1246 if (id.equals(ConfigPolicy.XML_CONFIG)) {
1247 filename = filename + ".xml";
1249 if (id.equals(ConfigPolicy.PROPERTIES_CONFIG)) {
1250 filename = filename + ".properties";
1252 if (id.equals(ConfigPolicy.OTHER_CONFIG)) {
1253 filename = filename + ".txt";
1259 private String[] getNameScopeAndVersionFromPdpPolicy(String fileName){
1260 String[] splitByDots = fileName.split("\\.");
1261 if(splitByDots.length < 3){
1262 //should we throw something
1265 String policyName = splitByDots[splitByDots.length-3];
1266 String version = splitByDots[splitByDots.length-2];
1267 //policy names now include version
1269 for(int i=0;i<splitByDots.length-3;i++){
1270 scope += ".".concat(splitByDots[i]);
1272 //remove the first dot
1273 if(scope.length() > 0){
1274 scope = scope.substring(1);
1276 String[] returnArray = new String[3];
1277 returnArray[0] = policyName + "." + version + ".xml";
1278 returnArray[2] = version;
1279 returnArray[1] = scope;
1283 //copied from StdEngine.java
1284 public static String createNewPDPGroupId(String name) {
1286 // replace "bad" characters with sequences that will be ok for file names and properties keys.
1287 id = id.replace(" ", "_sp_");
1288 id = id.replace("\t", "_tab_");
1289 id = id.replace("\\", "_bksl_");
1290 id = id.replace("/", "_sl_");
1291 id = id.replace(":", "_col_");
1292 id = id.replace("*", "_ast_");
1293 id = id.replace("?", "_q_");
1294 id = id.replace("\"", "_quo_");
1295 id = id.replace("<", "_lt_");
1296 id = id.replace(">", "_gt_");
1297 id = id.replace("|", "_bar_");
1298 id = id.replace("=", "_eq_");
1299 id = id.replace(",", "_com_");
1300 id = id.replace(";", "_scom_");
1306 * Checks if any of the given strings are empty or null
1307 * @param strings One or more Strings (or nulls) to check if they are null or empty
1308 * @return true if one or more of the given strings are empty or null
1310 private static boolean isNullOrEmpty(String... strings){
1311 for(String s : strings){
1312 if(!(s instanceof String)){
1323 private class PolicyDBDaoTransactionInstance implements PolicyDBDaoTransaction {
1324 private EntityManager em;
1325 private final Object emLock = new Object();
1330 private boolean operationRun = false;
1331 private final Thread transactionTimer;
1333 private PolicyDBDaoTransactionInstance(){
1334 //call the constructor with arguments
1335 this(Integer.parseInt(XACMLProperties.getProperty(XACMLRestProperties.PROP_PAP_TRANS_TIMEOUT)),
1336 Integer.parseInt(XACMLProperties.getProperty(XACMLRestProperties.PROP_PAP_TRANS_WAIT)));
1338 //timeout is how long the transaction can sit before rolling back
1339 //wait time is how long to wait for the transaction to start before throwing an exception
1340 private PolicyDBDaoTransactionInstance(int transactionTimeout, int transactionWaitTime){
1341 if(logger.isDebugEnabled()){
1342 logger.debug("\n\nPolicyDBDaoTransactionInstance() as PolicyDBDaoTransactionInstance() called:"
1343 + "\n transactionTimeout = " + transactionTimeout
1344 + "\n transactionWaitTime = " + transactionWaitTime + "\n\n");
1346 this.em = emf.createEntityManager();
1351 synchronized(emLock){
1353 startTransactionSynced(this.em,transactionWaitTime);
1354 } catch(Exception e){
1356 throw new PersistenceException("Could not lock transaction within "+transactionWaitTime+" milliseconds");
1359 class TransactionTimer implements Runnable {
1361 private int sleepTime;
1362 public TransactionTimer(int timeout){
1363 this.sleepTime = timeout;
1367 if(logger.isDebugEnabled()){
1368 Date date= new java.util.Date();
1369 logger.debug("\n\nTransactionTimer.run() - SLEEPING: "
1370 + "\n sleepTime (ms) = " + sleepTime
1371 + "\n TimeStamp = " + date.getTime()
1375 Thread.sleep(sleepTime);
1376 } catch (InterruptedException e) {
1377 //probably, the transaction was completed, the last thing we want to do is roll back
1378 if(logger.isDebugEnabled()){
1379 Date date= new java.util.Date();
1380 logger.debug("\n\nTransactionTimer.run() - WAKE Interrupt: "
1381 + "\n TimeStamp = " + date.getTime()
1384 Thread.currentThread().interrupt();
1387 if(logger.isDebugEnabled()){
1388 Date date= new java.util.Date();
1389 logger.debug("\n\nTransactionTimer.run() - WAKE Timeout: "
1390 + "\n TimeStamp = " + date.getTime()
1393 rollbackTransaction();
1398 transactionTimer = new Thread(new TransactionTimer(transactionTimeout),"transactionTimerThread");
1399 transactionTimer.start();
1404 private void checkBeforeOperationRun(){
1405 checkBeforeOperationRun(false);
1407 private void checkBeforeOperationRun(boolean justCheckOpen){
1408 if(!isTransactionOpen()){
1409 PolicyLogger.error("There is no transaction currently open");
1410 throw new IllegalStateException("There is no transaction currently open");
1412 if(operationRun && !justCheckOpen){
1413 PolicyLogger.error("An operation has already been performed and the current transaction should be committed");
1414 throw new IllegalStateException("An operation has already been performed and the current transaction should be committed");
1416 operationRun = true;
1419 public void commitTransaction() {
1420 synchronized(emLock){
1421 logger.debug("commitTransaction() as commitTransaction() called");
1422 if(!isTransactionOpen()){
1423 logger.warn("There is no open transaction to commit");
1426 } catch(Exception e){
1427 logger.error("Exception Occured"+e);
1432 em.getTransaction().commit();
1433 } catch(RollbackException e){
1434 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught RollbackException on em.getTransaction().commit()");
1435 throw new PersistenceException("The commit failed. Message:\n"+e.getMessage());
1440 if(newGroupId != null){
1442 notifyOthers(policyId,POLICY_NOTIFICATION,newGroupId);
1443 } catch(Exception e){
1444 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught Exception on notifyOthers("+policyId+","+POLICY_NOTIFICATION+","+newGroupId+")");
1448 notifyOthers(policyId,POLICY_NOTIFICATION);
1449 } catch(Exception e){
1450 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught Exception on notifyOthers("+policyId+","+POLICY_NOTIFICATION+")");
1455 //we don't want commit to fail just because this does
1456 if(newGroupId != null){
1458 notifyOthers(groupId,GROUP_NOTIFICATION,newGroupId);
1459 } catch(Exception e){
1460 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught Exception on notifyOthers("+groupId+","+GROUP_NOTIFICATION+","+newGroupId+")");
1464 notifyOthers(groupId,GROUP_NOTIFICATION);
1465 } catch(Exception e){
1466 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught Exception on notifyOthers("+groupId+","+GROUP_NOTIFICATION+")");
1471 //we don't want commit to fail just because this does
1473 notifyOthers(pdpId,PDP_NOTIFICATION);
1474 } catch(Exception e){
1475 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught Exception on notifyOthers("+pdpId+","+PDP_NOTIFICATION+")");
1479 if(transactionTimer instanceof Thread){
1480 transactionTimer.interrupt();
1485 public void rollbackTransaction() {
1486 logger.debug("rollbackTransaction() as rollbackTransaction() called");
1487 synchronized(emLock){
1488 if(isTransactionOpen()){
1491 em.getTransaction().rollback();
1492 } catch(Exception e){
1493 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Could not rollback transaction");
1497 }catch(Exception e){
1498 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Could not close EntityManager");
1504 }catch(Exception e){
1505 logger.warn("Could not close already closed transaction", e);
1510 if(transactionTimer instanceof Thread){
1511 transactionTimer.interrupt();
1517 private void createPolicy(PolicyRestAdapter policy, String username, String policyScope, String policyName, String policyDataString) {
1518 logger.debug("createPolicy(PolicyRestAdapter policy, String username, String policyScope, String policyName, String policyDataString) as createPolicy("+policy+", "+username+", "+policyScope+", "+policyName+", "+policyDataString+") called");
1519 synchronized(emLock){
1520 checkBeforeOperationRun();
1521 String configName = policyName;
1522 if(policyName.contains("Config_")){
1523 policyName = policyName.replace(".Config_", ":Config_");
1524 }else if(policyName.contains("Action_")){
1525 policyName = policyName.replace(".Action_", ":Action_");
1526 }else if(policyName.contains("Decision_")){
1527 policyName = policyName.replace(".Decision_", ":Decision_");
1529 policyName = policyName.split(":")[1];
1530 Query createPolicyQuery = em.createQuery("SELECT p FROM PolicyEntity p WHERE p.scope=:scope AND p.policyName=:policyName");
1531 createPolicyQuery.setParameter("scope", policyScope);
1532 createPolicyQuery.setParameter("policyName", policyName);
1533 List<?> createPolicyQueryList = createPolicyQuery.getResultList();
1534 PolicyEntity newPolicyEntity;
1536 if(createPolicyQueryList.size() < 1){
1537 newPolicyEntity = new PolicyEntity();
1539 } else if(createPolicyQueryList.size() > 1){
1540 PolicyLogger.error("Somehow, more than one policy with the same scope, name, and deleted status were found in the database");
1541 throw new PersistenceException("Somehow, more than one policy with the same scope, name, and deleted status were found in the database");
1543 newPolicyEntity = (PolicyEntity)createPolicyQueryList.get(0);
1547 ActionBodyEntity newActionBodyEntity = null;
1548 if(policy.getPolicyType().equals("Action")){
1549 boolean abupdate = false;
1550 if(newPolicyEntity.getActionBodyEntity() == null){
1551 newActionBodyEntity = new ActionBodyEntity();
1553 newActionBodyEntity = em.find(ActionBodyEntity.class, newPolicyEntity.getActionBodyEntity().getActionBodyId());
1557 if(newActionBodyEntity != null){
1559 em.persist(newActionBodyEntity);
1561 //build the file path
1562 //trim the .xml off the end
1563 String policyNameClean = FilenameUtils.removeExtension(configName);
1564 String actionBodyName = policyNameClean + ".json";
1565 Path actionBodyPath = Paths.get(Webapps.getActionHome(), actionBodyName);
1566 if(logger.isDebugEnabled()){
1567 logger.debug("\nPolicyDBDao.createPolicy"
1568 + "\n actionBodyPath = " + actionBodyPath);
1570 //get the action body
1571 String actionBodyString = null;
1572 String actionBodyPathStr = null;
1573 InputStream fileContentStream = null;
1575 if (Files.exists(actionBodyPath)) {
1577 actionBodyPathStr = (actionBodyPath != null ? actionBodyPath.toString() : null);
1578 fileContentStream = new FileInputStream(actionBodyPathStr);
1579 actionBodyString = IOUtils.toString(fileContentStream);
1580 if(logger.isDebugEnabled()){
1581 logger.debug("\nPolicyDBDao.createPolicy"
1582 + "\n actionBodyPathStr = " + actionBodyPathStr
1583 + "\n actionBodyString = " + actionBodyString);
1585 } catch (FileNotFoundException e) {
1586 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught FileNotFoundException on new actionBodyPathStr FileInputStream("+actionBodyPathStr+")");
1587 throw new IllegalArgumentException("The actionBodyPathStr file path " + actionBodyPathStr + " does not exist"
1588 + "\nEXCEPTION: " + e);
1589 } catch(IOException e2){
1590 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e2, "PolicyDBDao", "Caught IOException on actionBodyPath newIOUtils.toString("+fileContentStream+")");
1591 throw new IllegalArgumentException("The actionBodyPath file path cannot be read" + fileContentStream
1592 + "\nEXCEPTION: " + e2);
1594 IOUtils.closeQuietly(fileContentStream);
1597 if(actionBodyString == null){
1598 throw new IllegalArgumentException("The file path (" + actionBodyPathStr + ") cannot be read");
1601 actionBodyString = "{}";
1604 newActionBodyEntity.setActionBody(actionBodyString);
1605 newActionBodyEntity.setActionBodyName(actionBodyName);
1606 newActionBodyEntity.setModifiedBy("PolicyDBDao.createPolicy()");
1607 newActionBodyEntity.setDeleted(false);
1609 newActionBodyEntity.setCreatedBy("PolicyDBDao.createPolicy()");
1611 if(logger.isDebugEnabled()){
1612 logger.debug("\nPolicyDBDao.createPolicy"
1613 + "\n newActionBodyEntity.getActionBody() = " + newActionBodyEntity.getActionBody()
1614 + "\n newActionBodyEntity.getActionBodyName() = " + newActionBodyEntity.getActionBodyName()
1615 + "\n newActionBodyEntity.getModifiedBy() = " + newActionBodyEntity.getModifiedBy()
1616 + "\n newActionBodyEntity.getCreatedBy() = " + newActionBodyEntity.getCreatedBy()
1617 + "\n newActionBodyEntity.isDeleted() = " + newActionBodyEntity.isDeleted()
1618 + "\n FLUSHING to DB");
1620 //push the actionBodyEntity to the DB
1623 //newActionBodyEntity == null
1624 //We have a actionBody in the policy but we found no actionBody in the DB
1625 String msg = "\n\nPolicyDBDao.createPolicy - Incoming Action policy had an "
1626 + "actionBody, but it could not be found in the DB for update."
1627 + "\n policyScope = " + policyScope
1628 + "\n policyName = " + policyName + "\n\n";
1629 PolicyLogger.error("PolicyDBDao.createPolicy - Incoming Action policy had an actionBody, but it could not be found in the DB for update: policyName = " + policyName);
1630 throw new IllegalArgumentException(msg);
1634 ConfigurationDataEntity newConfigurationDataEntity;
1635 if(policy.getPolicyType().equals("Config")){
1636 boolean configUpdate;
1637 if(newPolicyEntity.getConfigurationData() == null){
1638 newConfigurationDataEntity = new ConfigurationDataEntity();
1639 configUpdate = false;
1641 newConfigurationDataEntity = em.find(ConfigurationDataEntity.class, newPolicyEntity.getConfigurationData().getConfigurationDataId());
1642 configUpdate = true;
1645 if(newConfigurationDataEntity != null){
1647 em.persist(newConfigurationDataEntity);
1649 if(!stringEquals(newConfigurationDataEntity.getConfigurationName(),getConfigFile(configName,policy))){
1650 newConfigurationDataEntity.setConfigurationName(getConfigFile(configName,policy));
1652 if(newConfigurationDataEntity.getConfigType() == null || !newConfigurationDataEntity.getConfigType().equals(policy.getConfigType())){
1653 newConfigurationDataEntity.setConfigType(policy.getConfigType());
1656 newConfigurationDataEntity.setCreatedBy(username);
1658 if(newConfigurationDataEntity.getModifiedBy() == null || !newConfigurationDataEntity.getModifiedBy().equals(username)){
1659 newConfigurationDataEntity.setModifiedBy(username);
1661 if(newConfigurationDataEntity.getDescription() == null || !newConfigurationDataEntity.getDescription().equals("")){
1662 newConfigurationDataEntity.setDescription("");
1664 if(newConfigurationDataEntity.getConfigBody() == null || newConfigurationDataEntity.getConfigBody().isEmpty() ||
1665 (!newConfigurationDataEntity.getConfigBody().equals(policy.getConfigBodyData()))){
1666 //hopefully one of these won't be null
1667 if(policy.getConfigBodyData() == null || policy.getConfigBodyData().isEmpty()){
1668 newConfigurationDataEntity.setConfigBody(policy.getJsonBody());
1670 newConfigurationDataEntity.setConfigBody(policy.getConfigBodyData());
1673 if(newConfigurationDataEntity.isDeleted() == true){
1674 newConfigurationDataEntity.setDeleted(false);
1679 //We have a configurationData body in the policy but we found no configurationData body in the DB
1680 String msg = "\n\nPolicyDBDao.createPolicy - Incoming Config policy had a "
1681 + "configurationData body, but it could not be found in the DB for update."
1682 + "\n policyScope = " + policyScope
1683 + "\n policyName = " + policyName + "\n\n";
1684 PolicyLogger.error("PolicyDBDao.createPolicy - Incoming Config policy had a configurationData body, but it could not be found in the DB for update: policyName = " + policyName);
1685 throw new IllegalArgumentException(msg);
1689 newConfigurationDataEntity = null;
1692 em.persist(newPolicyEntity);
1695 policyId = newPolicyEntity.getPolicyId();
1697 if(!stringEquals(newPolicyEntity.getPolicyName(),policyName)){
1698 newPolicyEntity.setPolicyName(policyName);
1700 if(!stringEquals(newPolicyEntity.getCreatedBy(),username)){
1701 newPolicyEntity.setCreatedBy(username);
1703 if(!stringEquals(newPolicyEntity.getDescription(),policy.getPolicyDescription())){
1704 newPolicyEntity.setDescription(policy.getPolicyDescription());
1706 if(!stringEquals(newPolicyEntity.getModifiedBy(),username)){
1707 newPolicyEntity.setModifiedBy(username);
1709 if(!stringEquals(newPolicyEntity.getPolicyData(),policyDataString)){
1710 newPolicyEntity.setPolicyData(policyDataString);
1712 if(!stringEquals(newPolicyEntity.getScope(),policyScope)){
1713 newPolicyEntity.setScope(policyScope);
1715 if(newPolicyEntity.isDeleted() == true){
1716 newPolicyEntity.setDeleted(false);
1718 newPolicyEntity.setConfigurationData(newConfigurationDataEntity);
1719 newPolicyEntity.setActionBodyEntity(newActionBodyEntity);
1723 this.policyId = newPolicyEntity.getPolicyId();
1729 @SuppressWarnings("unused")
1730 public PolicyEntity getPolicy(int policyID){
1731 return getPolicy(policyID,null,null);
1733 public PolicyEntity getPolicy(String policyName,String scope){
1734 return getPolicy(-1,policyName,scope);
1736 private PolicyEntity getPolicy(int policyID, String policyName,String scope){
1737 logger.debug("getPolicy(int policyId, String policyName) as getPolicy("+policyID+","+policyName+") called");
1738 if(policyID < 0 && isNullOrEmpty(policyName,scope)){
1739 throw new IllegalArgumentException("policyID must be at least 0 or policyName must be not null or blank");
1742 synchronized(emLock){
1743 checkBeforeOperationRun(true);
1744 //check if group exists
1747 if(!isNullOrEmpty(policyName,scope)){
1748 policyId = policyName;
1749 policyQuery = em.createQuery("SELECT p FROM PolicyEntity p WHERE p.policyName=:name AND p.scope=:scope");
1750 policyQuery.setParameter("name", policyId);
1751 policyQuery.setParameter("scope", scope);
1753 policyId = String.valueOf(policyID);
1754 policyQuery = em.createNamedQuery("PolicyEntity.FindById");
1755 policyQuery.setParameter("id", policyId);
1757 List<?> policyQueryList;
1759 policyQueryList = policyQuery.getResultList();
1760 }catch(Exception e){
1761 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught Exception trying to get policy with policyQuery.getResultList()");
1762 throw new PersistenceException("Query failed trying to get policy "+policyId);
1764 if(policyQueryList.size() < 1){
1765 PolicyLogger.error("Policy does not exist with id "+policyId);
1766 throw new PersistenceException("Group policy is being added to does not exist with id "+policyId);
1767 } else if(policyQueryList.size() > 1){
1768 PolicyLogger.error("Somehow, more than one policy with the id "+policyId+" were found in the database");
1769 throw new PersistenceException("Somehow, more than one policy with the id "+policyId+" were found in the database");
1771 return (PolicyEntity)policyQueryList.get(0);
1776 public void renamePolicy(String oldPath, String newPath,String username){
1777 /* String[] oldPolicy = getScopeAndNameAndType(oldPath);
1778 String[] newPolicy = getScopeAndNameAndType(newPath);
1779 if(oldPolicy == null || newPolicy == null){
1780 PolicyLogger.error(MessageCodes.ERROR_PROCESS_FLOW+"Could not parse one or more of the path names: "
1781 +oldPath+", "+newPath);
1782 throw new IllegalArgumentException("Could not parse one or more of the path names");
1784 synchronized (emLock) {
1785 checkBeforeOperationRun();
1787 PolicyEntity existingPolicy;
1788 boolean existingPolicyDeleted = false;
1789 List<?> groups = null;
1791 existingPolicy = getPolicy(newPolicy[1],newPolicy[0]);
1792 } catch(Exception e){
1793 existingPolicy = null;
1795 if(existingPolicy != null && !existingPolicy.isDeleted()){
1796 logger.error("The policy named "+existingPolicy.getPolicyName()+" already exists, cannot rename policy: "+newPolicy);
1797 throw new IllegalArgumentException("The policy named "+existingPolicy.getPolicyName()+" already exists, cannot rename policy: "+newPolicy);
1798 } else if(existingPolicy != null && existingPolicy.isDeleted()){
1800 Query getGroups = em.createQuery("SELECT g FROM GroupEntity g JOIN g.policies p WHERE p.policyId=:pid");
1802 getGroups.setParameter("pid", existingPolicy.getPolicyId());
1803 groups = getGroups.getResultList();
1804 }catch(Exception e){
1805 groups = new LinkedList<>();
1807 for(Object o : groups){
1808 GroupEntity group = (GroupEntity)o;
1809 group.removePolicyFromGroup(existingPolicy);
1813 }catch(Exception e){
1814 logger.error("Error while removing the policy from groups: "+existingPolicy.getPolicyName());
1817 em.remove(existingPolicy);
1819 }catch(Exception e){
1820 logger.error("Could not remove the existing deleted policy: "+existingPolicy.getPolicyName());
1822 existingPolicyDeleted = true;
1823 //create the new policy
1824 //for each of the groups, add the new policy
1827 PolicyEntity policyToRename;
1829 policyToRename = getPolicy(oldPolicy[1],oldPolicy[0]);
1830 } catch(Exception e){
1831 PolicyLogger.error(MessageCodes.ERROR_PROCESS_FLOW, e, "PolicyDBDao", "Could not get policy record to rename: "
1833 throw new PersistenceException("Could not get policy record to rename");
1835 String policyDataString = null;
1836 InputStream fileContentStream = null;
1837 String policyFilePath = Paths.get(oldPath).toAbsolutePath().toString();
1838 //I want to try the old path first, then if it doesn't work, try the new path
1839 for(int i=0;i<2;i++){
1841 fileContentStream = new FileInputStream(policyFilePath);
1842 policyDataString = IOUtils.toString(fileContentStream);
1843 } catch (FileNotFoundException e) {
1844 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught FileNotFoundException on new FileInputStream("+policyFilePath+")");
1845 //if we can't find the oldPath, we'll try the new path
1847 policyFilePath = Paths.get(newPath).toAbsolutePath().toString();
1850 throw new IllegalArgumentException("The file path does not exist");
1851 } catch(IOException e2){
1852 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e2, "PolicyDBDao", "Caught IOException on newIOUtils.toString("+fileContentStream+")");
1853 throw new IllegalArgumentException("The file path cannot be read");
1855 IOUtils.closeQuietly(fileContentStream);
1857 if(policyDataString == null){
1858 throw new IllegalArgumentException("The file path cannot be read");
1863 policyToRename.setPolicyName(newPolicy[1]);
1864 policyToRename.setPolicyData(policyDataString);
1865 policyToRename.setScope(newPolicy[0]);
1866 policyToRename.setModifiedBy(username);
1867 if(policyToRename.getConfigurationData() != null){
1868 String configType = policyToRename.getConfigurationData().getConfigType();
1869 policyToRename.getConfigurationData().setConfigurationName(getConfigFile(newPolicy[1], configType));
1870 policyToRename.getConfigurationData().setModifiedBy(username);
1872 if(policyToRename.getActionBodyEntity() != null){
1873 String newActionName = newPolicy[0]+"."+removeFileExtension(newPolicy[1])+".json";
1874 policyToRename.getActionBodyEntity().setActionBodyName(newActionName);
1875 policyToRename.getActionBodyEntity().setModifiedBy(username);
1877 if(existingPolicyDeleted){
1878 for(Object o : groups){
1880 GroupEntity group = (GroupEntity)o;
1881 group.addPolicyToGroup(policyToRename);
1885 this.policyId = policyToRename.getPolicyId();
1886 this.newGroupId = oldPath;
1891 public GroupEntity getGroup(long groupKey){
1892 logger.debug("getGroup(int groupKey) as getGroup("+groupKey+") called");
1894 throw new IllegalArgumentException("groupKey must be at least 0");
1896 synchronized(emLock){
1897 checkBeforeOperationRun(true);
1898 //check if group exists
1899 Query groupQuery = em.createQuery("SELECT g FROM GroupEntity g WHERE g.groupKey=:groupKey");
1900 groupQuery.setParameter("groupKey", groupKey);
1901 List<?> groupQueryList;
1903 groupQueryList = groupQuery.getResultList();
1904 }catch(Exception e){
1905 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught Exception trying to get group with groupQuery.getResultList()");
1906 throw new PersistenceException("Query failed trying to get group "+groupKey);
1908 if(groupQueryList.size() < 1){
1909 PolicyLogger.error("Group does not exist with groupKey "+groupKey);
1910 throw new PersistenceException("Group does not exist with groupKey "+groupKey);
1911 } else if(groupQueryList.size() > 1){
1912 PolicyLogger.error("Somehow, more than one group with the groupKey "+groupKey+" were found in the database");
1913 throw new PersistenceException("Somehow, more than one group with the groupKey "+groupKey+" were found in the database");
1915 return (GroupEntity)groupQueryList.get(0);
1920 public GroupEntity getGroup(String groupId){
1921 logger.debug("getGroup(String groupId) as getGroup("+groupId+") called");
1922 if(isNullOrEmpty(groupId)){
1923 throw new IllegalArgumentException("groupId must not be null or empty");
1925 synchronized(emLock){
1926 checkBeforeOperationRun(true);
1927 //check if group exists
1928 Query groupQuery = em.createQuery("SELECT g FROM GroupEntity g WHERE g.groupId=:groupId");
1929 groupQuery.setParameter("groupId", groupId);
1930 List<?> groupQueryList;
1932 groupQueryList = groupQuery.getResultList();
1933 }catch(Exception e){
1934 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught Exception trying to get group with groupQuery.getResultList()");
1935 throw new PersistenceException("Query failed trying to get group "+groupId);
1937 if(groupQueryList.size() < 1){
1938 PolicyLogger.error("Group does not exist with id "+groupId);
1939 throw new PersistenceException("Group does not exist with id "+groupId);
1940 } else if(groupQueryList.size() > 1){
1941 PolicyLogger.error("Somehow, more than one group with the id "+groupId+" were found in the database");
1942 throw new PersistenceException("Somehow, more than one group with the id "+groupId+" were found in the database");
1944 return (GroupEntity)groupQueryList.get(0);
1948 public List<?> getPdpsInGroup(long groupKey){
1949 logger.debug("getPdpsInGroup(int groupKey) as getPdpsInGroup("+groupKey+") called");
1951 throw new IllegalArgumentException("groupId must not be < 0");
1953 synchronized(emLock){
1954 checkBeforeOperationRun(true);
1955 Query pdpsQuery = em.createQuery("SELECT p FROM PdpEntity p WHERE p.groupEntity=:group");
1956 pdpsQuery.setParameter("group", getGroup(groupKey));
1957 return pdpsQuery.getResultList();
1961 public PdpEntity getPdp(long pdpKey){
1962 logger.debug("getPdp(int pdpKey) as getPdp("+pdpKey+") called");
1964 throw new IllegalArgumentException("pdpKey must be at least 0");
1966 synchronized(emLock){
1967 checkBeforeOperationRun(true);
1968 //check if group exists
1969 Query pdpQuery = em.createQuery("SELECT p FROM PdpEntity p WHERE p.pdpKey=:pdpKey");
1970 pdpQuery.setParameter("pdpKey", pdpKey);
1971 List<?> pdpQueryList;
1973 pdpQueryList = pdpQuery.getResultList();
1974 }catch(Exception e){
1975 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught Exception trying to get pdp with pdpQuery.getResultList()");
1976 throw new PersistenceException("Query failed trying to get pdp "+pdpKey);
1978 if(pdpQueryList.size() < 1){
1979 PolicyLogger.error("Pdp does not exist with pdpKey "+pdpKey);
1980 throw new PersistenceException("Pdp does not exist with pdpKey "+pdpKey);
1981 } else if(pdpQueryList.size() > 1){
1982 PolicyLogger.error("Somehow, more than one pdp with the pdpKey "+pdpKey+" were found in the database");
1983 throw new PersistenceException("Somehow, more than one pdp with the pdpKey "+pdpKey+" were found in the database");
1985 return (PdpEntity)pdpQueryList.get(0);
1989 public void deletePolicy(String policyToDeletes){
1990 /*synchronized(emLock){
1991 checkBeforeOperationRun();
1992 logger.debug("deletePolicy(String policyToDeletes) as deletePolicy("+policyToDeletes+") called");
1993 String[] scopeNameAndType = getScopeAndNameAndType(policyToDeletes);
1994 if(scopeNameAndType == null){
1995 throw new IllegalArgumentException("Could not parse file path");
1997 String realScope = scopeNameAndType[0];
1998 String realName = scopeNameAndType[1];
1999 Query deletePolicyQuery = em.createQuery("SELECT p FROM PolicyEntity p WHERE p.scope=:scope AND p.policyName=:policyName AND p.deleted=:deleted");
2000 deletePolicyQuery.setParameter("scope",realScope);
2001 deletePolicyQuery.setParameter("policyName", realName);
2002 deletePolicyQuery.setParameter("deleted", false);
2003 List<?> deletePolicyQueryList = deletePolicyQuery.getResultList();
2004 if(deletePolicyQueryList.size() < 1){
2005 logger.warn("The policy being deleted could not be found.");
2007 } else if(deletePolicyQueryList.size() > 1){
2008 PolicyLogger.error("Somehow, more than one policy with the same scope, name, and deleted status were found in the database");
2009 throw new PersistenceException("Somehow, more than one policy with the same scope, name, and deleted status were found in the database");
2011 PolicyEntity policyToDelete = (PolicyEntity)deletePolicyQueryList.get(0);
2012 policyToDelete.setDeleted(true);
2013 if(policyToDelete.getConfigurationData() != null){
2014 ConfigurationDataEntity cde = em.find(ConfigurationDataEntity.class,policyToDelete.getConfigurationData().getConfigurationDataId());
2016 cde.setDeleted(true);
2019 if(policyToDelete.getActionBodyEntity() != null){
2020 ActionBodyEntity abe = em.find(ActionBodyEntity.class,policyToDelete.getActionBodyEntity().getActionBodyId());
2022 abe.setDeleted(true);
2027 this.policyId = policyToDelete.getPolicyId();
2036 public boolean isTransactionOpen() {
2037 logger.debug("isTransactionOpen() as isTransactionOpen() called");
2038 synchronized(emLock){
2039 return em.isOpen() && em.getTransaction().isActive();
2045 public void clonePolicy(String oldPolicyPath, String newPolicyPath, String username){
2046 /*String[] oldPolicyData = getScopeAndNameAndType(oldPolicyPath);
2047 String[] newPolicyData = getScopeAndNameAndType(newPolicyPath);
2048 if(oldPolicyData == null || newPolicyData == null){
2049 PolicyLogger.error(MessageCodes.ERROR_PROCESS_FLOW+"Could not parse one or more of the path names: "
2050 +oldPolicyPath+", "+newPolicyPath);
2051 throw new IllegalArgumentException("Could not parse the oldPolicyPath or newPolicyPath");
2053 PolicyEntity oldPolicy;
2055 oldPolicy = getPolicy(oldPolicyData[1],oldPolicyData[0]);
2056 }catch(Exception e){
2057 PolicyLogger.error(MessageCodes.ERROR_PROCESS_FLOW, e, "PolicyDBDao", "Could not get policy record to clone: "
2059 throw new PersistenceException("Could not get policy record to clone");
2061 ConfigurationDataEntity clonedConfig = null;
2062 if(oldPolicy.getConfigurationData() != null){
2063 clonedConfig = new ConfigurationDataEntity();
2064 em.persist(clonedConfig);
2065 clonedConfig.setConfigBody(oldPolicy.getConfigurationData().getConfigBody());
2066 clonedConfig.setConfigType(oldPolicy.getConfigurationData().getConfigType());
2067 clonedConfig.setCreatedBy(username);
2068 clonedConfig.setConfigurationName(getConfigFile(newPolicyData[1], oldPolicy.getConfigurationData().getConfigType()));
2069 clonedConfig.setDescription(oldPolicy.getConfigurationData().getDescription());
2070 clonedConfig.setModifiedBy(username);
2073 ActionBodyEntity clonedAction = null;
2074 if(oldPolicy.getActionBodyEntity() != null){
2075 clonedAction = new ActionBodyEntity();
2076 em.persist(clonedAction);
2077 clonedAction.setActionBody(oldPolicy.getActionBodyEntity().getActionBody());
2078 clonedAction.setActionBodyName(newPolicyData[0]+"."+newPolicyData[1]+".json");
2079 clonedAction.setCreatedBy(username);
2080 clonedAction.setModifiedBy(username);
2087 private String processConfigPath(String configPath){
2088 String webappsPath = XACMLProperties.getProperty(XACMLRestProperties.PROP_PAP_WEBAPPS);
2089 if(webappsPath == null){
2090 logger.error("Webapps property does not exist");
2091 throw new IllegalArgumentException("Webapps property does not exist");
2093 configPath = configPath.replace("$URL", webappsPath);
2094 //make sure the correct slashes are in
2096 configPath = Paths.get(configPath).toString();
2097 } catch(InvalidPathException e){
2098 logger.error("Invalid config path: "+configPath, e);
2099 throw new IllegalArgumentException("Invalid config path: "+configPath);
2103 private String readConfigFile(String configPath){
2104 String configDataString = null;
2105 InputStream configContentStream = null;
2107 configContentStream = new FileInputStream(configPath);
2108 configDataString = IOUtils.toString(configContentStream);
2109 } catch (FileNotFoundException e) {
2110 logger.error("Caught FileNotFoundException on new FileInputStream("+configPath+")",e);
2111 throw new IllegalArgumentException("The config file path does not exist");
2112 } catch(IOException e2){
2113 logger.error("Caught IOException on newIOUtils.toString("+configContentStream+")",e2);
2114 throw new IllegalArgumentException("The config file path cannot be read");
2116 IOUtils.closeQuietly(configContentStream);
2118 if(configDataString == null){
2119 throw new IllegalArgumentException("The config file path cannot be read");
2121 return configDataString;
2125 public void createPolicy(Policy policy, String username){
2126 InputStream policyXmlStream = null;
2128 logger.debug("createPolicy(PolicyRestAdapter policy, String username) as createPolicy("+policy+","+username+") called");
2129 String policyScope = policy.policyAdapter.getDomainDir().replace(File.separator, ".");
2130 //Does not need to be XACMLPolicyWriterWithPapNotify since it is already in the PAP
2131 //and this transaction is intercepted up stream.
2132 String policyDataString;
2134 policyXmlStream = XACMLPolicyWriter.getXmlAsInputStream((PolicyType)policy.getCorrectPolicyDataObject());
2135 policyDataString = IOUtils.toString(policyXmlStream);
2136 } catch (IOException e) {
2137 policyDataString = "could not read";
2138 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught IOException on IOUtils.toString("+policyXmlStream+")");
2139 throw new IllegalArgumentException("Cannot parse the policy xml from the PolicyRestAdapter.");
2141 IOUtils.closeQuietly(policyXmlStream);
2142 String configPath = "";
2143 if (policy.policyAdapter.getPolicyType().equalsIgnoreCase("Config")) {
2144 configPath = evaluateXPath("/Policy/Rule/AdviceExpressions/AdviceExpression[contains(@AdviceId,'ID')]/AttributeAssignmentExpression[@AttributeId='URLID']/AttributeValue/text()", policyDataString);
2145 } else if (policy.policyAdapter.getPolicyType().equalsIgnoreCase("Action")) {
2146 configPath = evaluateXPath("/Policy/Rule/ObligationExpressions/ObligationExpression[contains(@ObligationId, " +policy.policyAdapter.getActionAttribute()+ ")]/AttributeAssignmentExpression[@AttributeId='body']/AttributeValue/text()", policyDataString);
2149 String prefix = null;
2150 if (policy.policyAdapter.getPolicyType().equalsIgnoreCase("Config")) {
2152 prefix = configPath.substring(configPath.indexOf(policyScope+".")+policyScope.concat(".").length(), configPath.indexOf(policy.policyAdapter.getPolicyName()));
2153 if(isNullOrEmpty(policy.policyAdapter.getConfigBodyData())){
2154 String configData = "";
2156 String newConfigPath = configPath;
2158 newConfigPath = processConfigPath(newConfigPath);
2159 }catch(Exception e2){
2160 logger.error("Could not process config path: "+newConfigPath,e2);
2162 configData = readConfigFile(newConfigPath);
2163 }catch(Exception e){
2164 logger.error("Could not read config body data for "+configPath,e);
2166 policy.policyAdapter.setConfigBodyData(configData);
2168 } else if (policy.policyAdapter.getPolicyType().equalsIgnoreCase("Action")) {
2170 } else if (policy.policyAdapter.getPolicyType().equalsIgnoreCase("Decision")) {
2171 prefix = "Decision_";
2174 if(!(policy.policyAdapter.getData() instanceof PolicyType)){
2175 PolicyLogger.error("The data field is not an instance of PolicyType");
2176 throw new IllegalArgumentException("The data field is not an instance of PolicyType");
2178 String finalName = policyScope + "." + prefix+policy.policyAdapter.getPolicyName()+"."+((PolicyType)policy.policyAdapter.getData()).getVersion()+".xml";
2179 if(policy.policyAdapter.getConfigType() == null || policy.policyAdapter.getConfigType().equals("")){
2180 //get the config file extension
2182 if (configPath != null) {
2183 if (!configPath.equalsIgnoreCase("")) {
2184 ext = configPath.substring(configPath.lastIndexOf('.'), configPath.length());;
2188 if(ext.contains("txt")){
2189 policy.policyAdapter.setConfigType(OTHER_CONFIG);
2190 } else if(ext.contains("json")){
2191 policy.policyAdapter.setConfigType(JSON_CONFIG);
2192 } else if(ext.contains("xml")){
2193 policy.policyAdapter.setConfigType(XML_CONFIG);
2194 } else if(ext.contains("properties")){
2195 policy.policyAdapter.setConfigType(PROPERTIES_CONFIG);
2197 if (policy.policyAdapter.getPolicyType().equalsIgnoreCase("Action")){
2198 policy.policyAdapter.setConfigType(JSON_CONFIG);
2203 createPolicy(policy.policyAdapter, username, policyScope,finalName,policyDataString);
2205 if(policyXmlStream != null){
2207 policyXmlStream.close();
2208 } catch (IOException e) {
2209 logger.error("Exception Occured while closing input stream"+e);
2216 public void close(){
2217 synchronized(emLock){
2219 if(em.getTransaction().isActive()){
2220 em.getTransaction().rollback();
2224 if(transactionTimer instanceof Thread){
2225 transactionTimer.interrupt();
2233 public void createGroup(String groupId, String groupName, String groupDescription, String username) {
2234 logger.debug("deletePolicy(String policyToDeletes) as createGroup("+groupId+", "+groupName+", "+groupDescription+") called");
2235 if(isNullOrEmpty(groupId, groupName, username)){
2236 throw new IllegalArgumentException("groupId, groupName, and username must not be null or empty");
2238 if(!(groupDescription instanceof String)){
2239 groupDescription = "";
2242 synchronized(emLock){
2243 checkBeforeOperationRun();
2244 Query checkGroupQuery = em.createQuery("SELECT g FROM GroupEntity g WHERE g.groupId=:groupId AND g.deleted=:deleted");
2245 checkGroupQuery.setParameter("groupId", groupId);
2246 checkGroupQuery.setParameter("deleted", false);
2247 List<?> checkGroupQueryList;
2249 checkGroupQueryList = checkGroupQuery.getResultList();
2250 } catch(Exception e){
2251 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught Exception on checkGroupQuery.getResultList()");
2252 throw new PersistenceException("Query failed trying to check for existing group");
2254 if(checkGroupQueryList.size() > 0){
2255 PolicyLogger.error("The group being added already exists with id "+groupId);
2256 throw new PersistenceException("The group being added already exists with id "+groupId);
2258 GroupEntity newGroup = new GroupEntity();
2259 em.persist(newGroup);
2260 newGroup.setCreatedBy(username);
2261 newGroup.setModifiedBy(username);
2262 newGroup.setGroupName(groupName);
2263 newGroup.setGroupId(groupId);
2264 newGroup.setDescription(groupDescription);
2267 this.groupId = newGroup.getGroupKey();
2272 public void updateGroup(OnapPDPGroup group, String username){
2273 logger.debug("updateGroup(PDPGroup group) as updateGroup("+group+","+username+") called");
2275 throw new IllegalArgumentException("PDPGroup group must not be null");
2277 if(isNullOrEmpty(group.getId(), username)){
2278 throw new IllegalArgumentException("group.getId() and username must not be null or empty");
2281 synchronized(emLock){
2282 checkBeforeOperationRun();
2283 Query getGroupQuery = em.createQuery("SELECT g FROM GroupEntity g WHERE g.groupId=:groupId AND g.deleted=:deleted");
2284 getGroupQuery.setParameter("groupId", group.getId());
2285 getGroupQuery.setParameter("deleted", false);
2286 List<?> getGroupQueryList;
2288 getGroupQueryList = getGroupQuery.getResultList();
2289 } catch(Exception e){
2290 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught Exception on getGroupQuery.getResultList()");
2291 throw new PersistenceException("Query failed trying to get group "+group.getId()+" for editing");
2293 if(getGroupQueryList.size() < 1){
2294 PolicyLogger.error("The group cannot be found to update with id "+group.getId());
2295 throw new PersistenceException("The group cannot be found to update with id "+group.getId());
2296 } else if(getGroupQueryList.size() > 1){
2297 PolicyLogger.error("Somehow, more than one group with the same id "+group.getId()+" and deleted status were found in the database");
2298 throw new PersistenceException("Somehow, more than one group with the same id "+group.getId()+" and deleted status were found in the database");
2300 GroupEntity groupToUpdate = (GroupEntity)getGroupQueryList.get(0);
2301 if(!stringEquals(groupToUpdate.getModifiedBy(), username)){
2302 groupToUpdate.setModifiedBy(username);
2304 if(group.getDescription() != null && !stringEquals(group.getDescription(),groupToUpdate.getDescription())){
2305 groupToUpdate.setDescription(group.getDescription());
2307 //let's find out what policies have been deleted
2308 StdPDPGroup oldGroup = null;
2310 oldGroup = (StdPDPGroup) papEngine.getGroup(group.getId());
2311 } catch (PAPException e1) {
2312 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e1, "PolicyDBDao", "We cannot get the group from the papEngine to delete policies");
2314 if(oldGroup == null){
2315 PolicyLogger.error("We cannot get the group from the papEngine to delete policies");
2318 Set<String> newPolicySet = new HashSet<>(group.getPolicies().size());
2319 //a multiple of n runtime is faster than n^2, so I am using a hashset to do the comparison
2320 for(PDPPolicy pol: group.getPolicies()){
2321 newPolicySet.add(pol.getId());
2323 for(PDPPolicy pol : oldGroup.getPolicies()){
2324 //should be fast since getPolicies uses a HashSet in StdPDPGroup
2325 if(!newPolicySet.contains(pol.getId())){
2326 String[] scopeAndName = getNameScopeAndVersionFromPdpPolicy(pol.getId());
2327 PolicyEntity policyToDelete;
2329 policyToDelete = getPolicy(scopeAndName[0],scopeAndName[1]);
2330 }catch(Exception e){
2331 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Could not get policy to remove: "+pol.getId());
2332 throw new PersistenceException("Could not get policy to remove: "+pol.getId());
2334 groupToUpdate.getPolicies().remove(policyToDelete);
2339 if(group.getName() != null && !stringEquals(group.getName(),groupToUpdate.getgroupName())){
2340 //we need to check if the new id exists in the database
2341 String newGroupId = createNewPDPGroupId(group.getName());
2342 Query checkGroupQuery = em.createQuery("SELECT g FROM GroupEntity g WHERE g.groupId=:groupId AND g.deleted=:deleted");
2343 checkGroupQuery.setParameter("groupId", newGroupId);
2344 checkGroupQuery.setParameter("deleted", false);
2345 List<?> checkGroupQueryList;
2347 checkGroupQueryList = checkGroupQuery.getResultList();
2348 } catch(Exception e){
2349 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught Exception on checkGroupQuery.getResultList()");
2350 throw new PersistenceException("Query failed trying to check for existing group");
2352 if(checkGroupQueryList.size() != 0){
2353 PolicyLogger.error("The new group name already exists, group id "+newGroupId);
2354 throw new PersistenceException("The new group name already exists, group id "+newGroupId);
2356 groupToUpdate.setGroupId(newGroupId);
2357 groupToUpdate.setGroupName(group.getName());
2358 this.newGroupId = group.getId();
2362 this.groupId = groupToUpdate.getGroupKey();
2367 public void addPdpToGroup(String pdpID, String groupID, String pdpName, String pdpDescription, int pdpJmxPort, String username) {
2368 logger.debug("addPdpToGroup(String pdpID, String groupID, String pdpName, String pdpDescription, int pdpJmxPort, String username) as addPdpToGroup("+pdpID+", "+groupID+", "+pdpName+", "+pdpDescription+", "+pdpJmxPort+", "+username+") called");
2369 if(isNullOrEmpty(pdpID, groupID,pdpName,username)){
2370 throw new IllegalArgumentException("pdpID, groupID, pdpName, and username must not be null or empty");
2372 if(!(pdpDescription instanceof String)){
2373 pdpDescription = "";
2375 synchronized(emLock){
2376 checkBeforeOperationRun();
2377 Query checkGroupQuery = em.createQuery("SELECT g FROM GroupEntity g WHERE g.groupId=:groupId AND g.deleted=:deleted");
2378 checkGroupQuery.setParameter("groupId", groupID);
2379 checkGroupQuery.setParameter("deleted", false);
2380 List<?> checkGroupQueryList;
2382 checkGroupQueryList = checkGroupQuery.getResultList();
2383 } catch(Exception e){
2384 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught Exception trying to check for existing group on checkGroupQuery.getResultList()");
2385 throw new PersistenceException("Query failed trying to check for existing group");
2387 if(checkGroupQueryList.size() != 1){
2388 PolicyLogger.error("The group does not exist");
2389 throw new PersistenceException("The group does not exist");
2391 Query checkDuplicateQuery = em.createQuery("SELECT p FROM PdpEntity p WHERE p.pdpId=:pdpId AND p.deleted=:deleted");
2392 checkDuplicateQuery.setParameter("pdpId", pdpID);
2393 checkDuplicateQuery.setParameter("deleted", false);
2394 List<?> checkDuplicateList;
2396 checkDuplicateList = checkDuplicateQuery.getResultList();
2397 } catch(Exception e){
2398 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught Exception trying to check for duplicate PDP "+pdpID+" on checkDuplicateQuery.getResultList()");
2399 throw new PersistenceException("Query failed trying to check for duplicate PDP "+pdpID);
2402 if(checkDuplicateList.size() > 0){
2403 logger.warn("PDP already exists with id "+pdpID);
2404 newPdp = (PdpEntity)checkDuplicateList.get(0);
2406 newPdp = new PdpEntity();
2410 newPdp.setCreatedBy(username);
2411 newPdp.setDeleted(false);
2412 newPdp.setDescription(pdpDescription);
2413 newPdp.setGroup((GroupEntity)checkGroupQueryList.get(0));
2414 newPdp.setJmxPort(pdpJmxPort);
2415 newPdp.setModifiedBy(username);
2416 newPdp.setPdpId(pdpID);
2417 newPdp.setPdpName(pdpName);
2420 this.pdpId = newPdp.getPdpKey();
2427 public void updatePdp(OnapPDP pdp, String username){
2428 logger.debug("updatePdp(PDP pdp, String username) as updatePdp("+pdp+","+username+") called");
2430 throw new IllegalArgumentException("PDP pdp must not be null");
2432 if(isNullOrEmpty(pdp.getId(),username)){
2433 throw new IllegalArgumentException("pdp.getId() and username must not be null or empty");
2436 synchronized(emLock){
2437 checkBeforeOperationRun();
2438 Query getPdpQuery = em.createQuery("SELECT p FROM PdpEntity p WHERE p.pdpId=:pdpId AND p.deleted=:deleted");
2439 getPdpQuery.setParameter("pdpId", pdp.getId());
2440 getPdpQuery.setParameter("deleted", false);
2441 List<?> getPdpQueryList;
2443 getPdpQueryList = getPdpQuery.getResultList();
2444 } catch(Exception e){
2445 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught Exception on getPdpQuery.getResultList()");
2446 throw new PersistenceException("Query failed trying to get PDP "+pdp.getId());
2448 if(getPdpQueryList.size() < 1){
2449 PolicyLogger.error("The pdp cannot be found to update with id "+pdp.getId());
2450 throw new PersistenceException("The pdp cannot be found to update with id "+pdp.getId());
2451 } else if(getPdpQueryList.size() > 1){
2452 PolicyLogger.error("Somehow, more than one pdp with the same id "+pdp.getId()+" and deleted status were found in the database");
2453 throw new PersistenceException("Somehow, more than one pdp with the same id "+pdp.getId()+" and deleted status were found in the database");
2455 PdpEntity pdpToUpdate = (PdpEntity)getPdpQueryList.get(0);
2456 if(!stringEquals(pdpToUpdate.getModifiedBy(), username)){
2457 pdpToUpdate.setModifiedBy(username);
2459 if(pdp.getDescription() != null && !stringEquals(pdp.getDescription(),pdpToUpdate.getDescription())){
2460 pdpToUpdate.setDescription(pdp.getDescription());
2462 if(pdp.getName() != null && !stringEquals(pdp.getName(),pdpToUpdate.getPdpName())){
2463 pdpToUpdate.setPdpName(pdp.getName());
2465 if(pdp.getJmxPort() != null && !pdp.getJmxPort().equals(pdpToUpdate.getJmxPort())){
2466 pdpToUpdate.setJmxPort(pdp.getJmxPort());
2470 this.pdpId = pdpToUpdate.getPdpKey();
2475 public void movePdp(OnapPDP pdp, OnapPDPGroup group, String username){
2476 logger.debug("movePdp(PDP pdp, PDPGroup group, String username) as movePdp("+pdp+","+group+","+username+") called");
2477 if(pdp == null || group == null){
2478 throw new IllegalArgumentException("PDP pdp and PDPGroup group must not be null");
2480 if(isNullOrEmpty(username,pdp.getId(),group.getId())){
2481 throw new IllegalArgumentException("pdp.getId(), group.getId(), and username must not be null or empty");
2484 synchronized(emLock){
2485 checkBeforeOperationRun();
2486 //check if pdp exists
2487 Query getPdpQuery = em.createQuery("SELECT p FROM PdpEntity p WHERE p.pdpId=:pdpId AND p.deleted=:deleted");
2488 getPdpQuery.setParameter("pdpId", pdp.getId());
2489 getPdpQuery.setParameter("deleted", false);
2490 List<?> getPdpQueryList;
2492 getPdpQueryList = getPdpQuery.getResultList();
2493 } catch(Exception e){
2494 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught Exception on getPdpQuery.getResultList()");
2495 throw new PersistenceException("Query failed trying to get pdp to move with id "+pdp.getId());
2497 if(getPdpQueryList.size() < 1){
2498 PolicyLogger.error("The pdp cannot be found to move with id "+pdp.getId());
2499 throw new PersistenceException("The pdp cannot be found to move with id "+pdp.getId());
2500 } else if(getPdpQueryList.size() > 1){
2501 PolicyLogger.error("Somehow, more than one pdp with the same id "+pdp.getId()+" and deleted status were found in the database");
2502 throw new PersistenceException("Somehow, more than one pdp with the same id "+pdp.getId()+" and deleted status were found in the database");
2505 //check if new group exists
2506 Query checkGroupQuery = em.createQuery("SELECT g FROM GroupEntity g WHERE g.groupId=:groupId AND g.deleted=:deleted");
2507 checkGroupQuery.setParameter("groupId", group.getId());
2508 checkGroupQuery.setParameter("deleted", false);
2509 List<?> checkGroupQueryList;
2511 checkGroupQueryList = checkGroupQuery.getResultList();
2512 } catch(Exception e){
2513 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught Exception trying to get group on checkGroupQuery.getResultList()");
2514 throw new PersistenceException("Query failed trying to get new group "+group.getId());
2516 if(checkGroupQueryList.size() != 1){
2517 PolicyLogger.error("The group "+group.getId()+" does not exist");
2518 throw new PersistenceException("The group "+group.getId()+" does not exist");
2520 GroupEntity groupToMoveInto = (GroupEntity)checkGroupQueryList.get(0);
2521 PdpEntity pdpToUpdate = (PdpEntity)getPdpQueryList.get(0);
2522 pdpToUpdate.setGroup(groupToMoveInto);
2523 if(!stringEquals(pdpToUpdate.getModifiedBy(), username)){
2524 pdpToUpdate.setModifiedBy(username);
2528 this.pdpId = pdpToUpdate.getPdpKey();
2533 public void changeDefaultGroup(OnapPDPGroup group, String username){
2534 logger.debug("changeDefaultGroup(PDPGroup group, String username) as changeDefaultGroup("+group+","+username+") called");
2536 throw new IllegalArgumentException("PDPGroup group must not be null");
2538 if(isNullOrEmpty(group.getId(),username)){
2539 throw new IllegalArgumentException("group.getId() and username must not be null or empty");
2542 synchronized(emLock){
2543 checkBeforeOperationRun();
2544 Query getGroupQuery = em.createQuery("SELECT g FROM GroupEntity g WHERE g.groupId=:groupId AND g.deleted=:deleted");
2545 getGroupQuery.setParameter("groupId", group.getId());
2546 getGroupQuery.setParameter("deleted", false);
2547 List<?> getGroupQueryList;
2549 getGroupQueryList = getGroupQuery.getResultList();
2550 } catch(Exception e){
2551 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught Exception on getGroupQuery.getResultList()");
2552 throw new PersistenceException("Query failed trying to get group "+group.getId());
2554 if(getGroupQueryList.size() < 1){
2555 PolicyLogger.error("The group cannot be found to set default with id "+group.getId());
2556 throw new PersistenceException("The group cannot be found to set default with id "+group.getId());
2557 } else if(getGroupQueryList.size() > 1){
2558 PolicyLogger.error("Somehow, more than one group with the same id "+group.getId()+" and deleted status were found in the database");
2559 throw new PersistenceException("Somehow, more than one group with the same id "+group.getId()+" and deleted status were found in the database");
2561 GroupEntity newDefaultGroup = (GroupEntity)getGroupQueryList.get(0);
2562 newDefaultGroup.setDefaultGroup(true);
2563 if(!stringEquals(newDefaultGroup.getModifiedBy(), username)){
2564 newDefaultGroup.setModifiedBy(username);
2568 this.groupId = newDefaultGroup.getGroupKey();
2569 Query setAllGroupsNotDefault = em.createQuery("UPDATE GroupEntity g SET g.defaultGroup=:defaultGroup WHERE g.deleted=:deleted AND g.groupKey<>:groupKey");
2570 //not going to set modified by for all groups
2571 setAllGroupsNotDefault.setParameter("defaultGroup", false);
2572 setAllGroupsNotDefault.setParameter("deleted", false);
2573 setAllGroupsNotDefault.setParameter("groupKey", newDefaultGroup.getGroupKey());
2575 logger.info("set " + setAllGroupsNotDefault.executeUpdate() + " groups as not default");
2576 } catch(Exception e){
2577 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught Exception on setAllGroupsNotDefault.executeUpdate()");
2578 throw new PersistenceException("Could not set all other groups default to false");
2587 public void deleteGroup(OnapPDPGroup group, OnapPDPGroup moveToGroup, String username) throws PAPException {
2588 logger.debug("deleteGroup(PDPGroup group, PDPGroup moveToGroup, String username) as deleteGroup("+group+", "+moveToGroup+","+username+") called");
2590 throw new IllegalArgumentException("PDPGroup group cannot be null");
2592 if(isNullOrEmpty(username,group.getId())){
2593 throw new IllegalArgumentException("group.getId() and and username must not be null or empty");
2596 if(group.isDefaultGroup()){
2597 PolicyLogger.error("The default group "+group.getId()+" was attempted to be deleted. It cannot be.");
2598 throw new PAPException("You cannot delete the default group.");
2600 synchronized(emLock){
2601 checkBeforeOperationRun();
2602 Query deleteGroupQuery = em.createQuery("SELECT g FROM GroupEntity g WHERE g.groupId=:groupId AND g.deleted=:deleted");
2603 deleteGroupQuery.setParameter("groupId", group.getId());
2604 deleteGroupQuery.setParameter("deleted", false);
2605 List<?> deleteGroupQueryList;
2607 deleteGroupQueryList = deleteGroupQuery.getResultList();
2608 } catch(Exception e){
2609 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught Exception trying to check if group exists deleteGroupQuery.getResultList()");
2610 throw new PersistenceException("Query failed trying to check if group exists");
2612 if(deleteGroupQueryList.size() < 1){
2613 logger.warn("The group could not be found with id " + group.getId());
2615 } else if(deleteGroupQueryList.size() > 1){
2616 PolicyLogger.error("Somehow, more than one group with the id "+group.getId()+" were found in the database that are not deleted");
2617 throw new PersistenceException("Somehow, more than one group with the id "+group.getId()+" were found in the database that are not deleted");
2620 Query pdpsInGroupQuery = em.createQuery("SELECT p FROM PdpEntity p WHERE p.groupEntity=:group and p.deleted=:deleted");
2621 pdpsInGroupQuery.setParameter("group", ((GroupEntity)deleteGroupQueryList.get(0)));
2622 pdpsInGroupQuery.setParameter("deleted", false);
2623 List<?> pdpsInGroupList;
2625 pdpsInGroupList = pdpsInGroupQuery.getResultList();
2626 } catch(Exception e){
2627 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught Exception trying to get PDPs in group on pdpsInGroupQuery.getResultList()");
2628 throw new PersistenceException("Query failed trying to get PDPs in group");
2630 if(pdpsInGroupList.size() > 0){
2631 if(moveToGroup != null){
2632 Query checkMoveToGroupQuery = em.createQuery("SELECT o FROM GroupEntity o WHERE o.groupId=:groupId AND o.deleted=:deleted");
2633 checkMoveToGroupQuery.setParameter("groupId", moveToGroup.getId());
2634 checkMoveToGroupQuery.setParameter("deleted", false);
2635 List<?> checkMoveToGroupList;
2637 checkMoveToGroupList = checkMoveToGroupQuery.getResultList();
2638 } catch(Exception e){
2639 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught Exception trying to check if group exists checkMoveToGroupQuery.getResultList()");
2640 throw new PersistenceException("Query failed trying to check if group exists");
2642 if(checkMoveToGroupList.size() < 1){
2643 PolicyLogger.error("The group could not be found with id " + moveToGroup.getId());
2644 throw new PersistenceException("The group could not be found with id " + moveToGroup.getId());
2645 } else if(checkMoveToGroupList.size() > 1){
2646 PolicyLogger.error("Somehow, more than one group with the id "+moveToGroup.getId()+" were found in the database that are not deleted");
2647 throw new PersistenceException("Somehow, more than one group with the id "+moveToGroup.getId()+" were found in the database that are not deleted");
2649 GroupEntity newGroup = (GroupEntity)checkMoveToGroupList.get(0);
2650 for(Object pdpObject : pdpsInGroupList){
2651 PdpEntity pdp = (PdpEntity)pdpObject;
2652 pdp.setGroup(newGroup);
2653 if(!stringEquals(pdp.getModifiedBy(),username)){
2654 pdp.setModifiedBy(username);
2659 this.newGroupId = newGroup.getGroupId();
2660 } catch(PersistenceException e){
2661 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught PersistenceException trying to set pdp group to null on em.flush()");
2662 throw new PersistenceException("Query failed trying to set pdp group to ");
2667 PolicyLogger.error("Group "+group.getId()+" is trying to be delted with PDPs. No group was provided to move them to");
2668 throw new PAPException("Group has PDPs. Must provide a group for them to move to");
2673 GroupEntity groupToDelete = (GroupEntity)deleteGroupQueryList.get(0);
2674 groupToDelete.setDeleted(true);
2675 if(!stringEquals(groupToDelete.getModifiedBy(), username)){
2676 groupToDelete.setModifiedBy(username);
2679 this.groupId = groupToDelete.getGroupKey();
2684 public void addPolicyToGroup(String groupID, String policyID, String username) {
2685 logger.debug("addPolicyToGroup(String groupID, String policyID, String username) as addPolicyToGroup("+groupID+", "+policyID+","+username+") called");
2686 if(isNullOrEmpty(groupID, policyID, username)){
2687 throw new IllegalArgumentException("groupID, policyID, and username must not be null or empty");
2689 synchronized(emLock){
2690 checkBeforeOperationRun();
2691 //check if group exists
2692 Query groupQuery = em.createQuery("SELECT g FROM GroupEntity g WHERE g.groupId=:groupId AND g.deleted=:deleted");
2693 groupQuery.setParameter("groupId", groupID);
2694 groupQuery.setParameter("deleted", false);
2695 List<?> groupQueryList;
2697 groupQueryList = groupQuery.getResultList();
2698 }catch(Exception e){
2699 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught Exception trying to check if group exists groupQuery.getResultList()");
2700 throw new PersistenceException("Query failed trying to check if group "+groupID+" exists");
2702 if(groupQueryList.size() < 1){
2703 PolicyLogger.error("Group policy is being added to does not exist with id "+groupID);
2704 throw new PersistenceException("Group policy is being added to does not exist with id "+groupID);
2705 } else if(groupQueryList.size() > 1){
2706 PolicyLogger.error("Somehow, more than one group with the id "+groupID+" were found in the database that are not deleted");
2707 throw new PersistenceException("Somehow, more than one group with the id "+groupID+" were found in the database that are not deleted");
2709 //we need to convert the form of the policy id that is used groups into the form that is used
2710 //for the database. (com.Config_mypol.1.xml) to (Config_mypol.xml)
2711 String[] policyNameScopeAndVersion = getNameScopeAndVersionFromPdpPolicy(policyID);
2712 Query policyQuery = em.createQuery("SELECT p FROM PolicyEntity p WHERE p.policyName=:policyName AND p.scope=:scope AND p.deleted=:deleted");
2713 policyQuery.setParameter("policyName", policyNameScopeAndVersion[0]);
2714 policyQuery.setParameter("scope", policyNameScopeAndVersion[1]);
2715 policyQuery.setParameter("deleted", false);
2716 List<?> policyQueryList;
2718 policyQueryList = policyQuery.getResultList();
2719 } catch(Exception e){
2721 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught Exception trying to check if policy exists policyQuery.getResultList()");
2722 throw new PersistenceException("Query failed trying to check if policy "+policyNameScopeAndVersion[0]+" exists");
2724 if(policyQueryList.size() < 1){
2725 PolicyLogger.error("Policy being added to the group does not exist with policy id "+policyNameScopeAndVersion[0]);
2726 throw new PersistenceException("Policy being added to the group does not exist with policy id "+policyNameScopeAndVersion[0]);
2727 } else if(policyQueryList.size() > 1){
2728 PolicyLogger.error("Somehow, more than one policy with the id "+policyNameScopeAndVersion[0]+" were found in the database that are not deleted");
2729 throw new PersistenceException("Somehow, more than one group with the id "+policyNameScopeAndVersion[0]+" were found in the database that are not deleted");
2731 GroupEntity group = (GroupEntity)groupQueryList.get(0);
2732 PolicyEntity policy = (PolicyEntity)policyQueryList.get(0);
2733 Iterator<PolicyEntity> policyIt = group.getPolicies().iterator();
2734 String policyName = getPolicyNameAndVersionFromPolicyFileName(policy.getPolicyName())[0];
2736 while(policyIt.hasNext()){
2737 PolicyEntity pol = policyIt.next();
2738 if(getPolicyNameAndVersionFromPolicyFileName(pol.getPolicyName())[0].equals(policyName)){
2742 }catch(Exception e){
2744 PolicyLogger.error("Could not delete old versions for policy "+policy.getPolicyName()+", ID: "+policy.getPolicyId());
2746 group.addPolicyToGroup(policy);
2751 //this means delete pdp not just remove from group
2753 public void removePdpFromGroup(String pdpID, String username) {
2754 logger.debug("removePdpFromGroup(String pdpID, String username) as removePdpFromGroup("+pdpID+","+username+") called");
2755 if(isNullOrEmpty(pdpID,username)){
2756 throw new IllegalArgumentException("pdpID and username must not be null or empty");
2758 synchronized(emLock){
2759 checkBeforeOperationRun();
2760 Query pdpQuery = em.createQuery("SELECT p FROM PdpEntity p WHERE p.pdpId=:pdpId AND p.deleted=:deleted");
2761 pdpQuery.setParameter("pdpId", pdpID);
2762 pdpQuery.setParameter("deleted", false);
2765 pdpList = pdpQuery.getResultList();
2766 } catch(Exception e){
2767 PolicyLogger.error(MessageCodes.EXCEPTION_ERROR, e, "PolicyDBDao", "Caught Exception trying to check if pdp exists pdpQuery.getResultList()");
2768 throw new PersistenceException("Query failed trying to check if pdp "+pdpID+" exists");
2770 if(pdpList.size() > 1){
2771 PolicyLogger.error("Somehow, more than one pdp with the id "+pdpID+" were found in the database that are not deleted");
2772 throw new PersistenceException("Somehow, more than one pdp with the id "+pdpID+" were found in the database that are not deleted");
2773 } else if(pdpList.size() < 1){
2774 PolicyLogger.error("Pdp being removed does not exist with id "+pdpID);
2777 PdpEntity pdp = (PdpEntity)pdpList.get(0);
2779 if(!stringEquals(pdp.getModifiedBy(),username)){
2780 pdp.setModifiedBy(username);
2782 pdp.setDeleted(true);
2785 this.pdpId = pdp.getPdpKey();
2790 private PolicyDBDao(){
2794 public static PolicyDBDaoTestClass getPolicyDBDaoTestClass(){
2795 return new PolicyDBDao().new PolicyDBDaoTestClass();
2798 final class PolicyDBDaoTestClass {
2799 String getConfigFile(String filename, String scope, PolicyRestAdapter policy){
2800 return scope + "." + PolicyDBDao.this.getConfigFile(filename, policy);
2802 String computeScope(String fullPath, String pathToExclude){
2803 return PolicyDBDao.computeScope(fullPath, pathToExclude);
2805 String encryptPassword(String password) throws Exception{
2806 return PolicyDBDao.encryptPassword(password);
2808 String decryptPassword(String password) throws Exception{
2809 return PolicyDBDao.decryptPassword(password);
2811 String getDescriptionFromXacml(String xacmlData){
2812 return PolicyDBDao.getDescriptionFromXacml(xacmlData);
2814 String[] getPolicyNameAndVersionFromPolicyFileName(String originalPolicyName){
2815 return PolicyDBDao.this.getPolicyNameAndVersionFromPolicyFileName(originalPolicyName);