3cae650a31fe9beb9f5408e5015b5458f092cc73
[policy/models.git] / models-provider / src / main / java / org / onap / policy / models / provider / impl / DatabasePolicyModelsProviderImpl.java
1 /*-
2  * ============LICENSE_START=======================================================
3  *  Copyright (C) 2019-2020 Nordix Foundation.
4  *  Modifications Copyright (C) 2019 AT&T Intellectual Property. All rights reserved.
5  * ================================================================================
6  * Licensed under the Apache License, Version 2.0 (the "License");
7  * you may not use this file except in compliance with the License.
8  * You may obtain a copy of the License at
9  *
10  *      http://www.apache.org/licenses/LICENSE-2.0
11  *
12  * Unless required by applicable law or agreed to in writing, software
13  * distributed under the License is distributed on an "AS IS" BASIS,
14  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15  * See the License for the specific language governing permissions and
16  * limitations under the License.
17  *
18  * SPDX-License-Identifier: Apache-2.0
19  * ============LICENSE_END=========================================================
20  */
21
22 package org.onap.policy.models.provider.impl;
23
24 import java.util.Base64;
25 import java.util.Date;
26 import java.util.List;
27 import java.util.Map;
28 import java.util.Properties;
29
30 import javax.ws.rs.core.Response;
31
32 import lombok.NonNull;
33
34 import org.eclipse.persistence.config.PersistenceUnitProperties;
35 import org.onap.policy.models.base.PfModelException;
36 import org.onap.policy.models.base.PfModelRuntimeException;
37 import org.onap.policy.models.dao.DaoParameters;
38 import org.onap.policy.models.dao.PfDao;
39 import org.onap.policy.models.dao.PfDaoFactory;
40 import org.onap.policy.models.dao.impl.DefaultPfDao;
41 import org.onap.policy.models.pdp.concepts.Pdp;
42 import org.onap.policy.models.pdp.concepts.PdpGroup;
43 import org.onap.policy.models.pdp.concepts.PdpGroupFilter;
44 import org.onap.policy.models.pdp.concepts.PdpStatistics;
45 import org.onap.policy.models.pdp.concepts.PdpSubGroup;
46 import org.onap.policy.models.pdp.persistence.provider.PdpProvider;
47 import org.onap.policy.models.pdp.persistence.provider.PdpStatisticsProvider;
48 import org.onap.policy.models.provider.PolicyModelsProvider;
49 import org.onap.policy.models.provider.PolicyModelsProviderParameters;
50 import org.onap.policy.models.tosca.authorative.concepts.ToscaPolicy;
51 import org.onap.policy.models.tosca.authorative.concepts.ToscaPolicyFilter;
52 import org.onap.policy.models.tosca.authorative.concepts.ToscaPolicyIdentifier;
53 import org.onap.policy.models.tosca.authorative.concepts.ToscaPolicyType;
54 import org.onap.policy.models.tosca.authorative.concepts.ToscaPolicyTypeFilter;
55 import org.onap.policy.models.tosca.authorative.concepts.ToscaPolicyTypeIdentifier;
56 import org.onap.policy.models.tosca.authorative.concepts.ToscaServiceTemplate;
57 import org.onap.policy.models.tosca.authorative.provider.AuthorativeToscaProvider;
58 import org.onap.policy.models.tosca.legacy.concepts.LegacyGuardPolicyInput;
59 import org.onap.policy.models.tosca.legacy.concepts.LegacyGuardPolicyOutput;
60 import org.onap.policy.models.tosca.legacy.concepts.LegacyOperationalPolicy;
61 import org.onap.policy.models.tosca.legacy.provider.LegacyProvider;
62 import org.slf4j.Logger;
63 import org.slf4j.LoggerFactory;
64
65 /**
66  * This class provides an implementation of the Policy Models Provider for the ONAP Policy Framework that works towards
67  * a relational database.
68  *
69  * @author Liam Fallon (liam.fallon@est.tech)
70  */
71 public class DatabasePolicyModelsProviderImpl implements PolicyModelsProvider {
72
73     private static final Logger LOGGER = LoggerFactory.getLogger(DatabasePolicyModelsProviderImpl.class);
74
75     private final PolicyModelsProviderParameters parameters;
76
77     // Database connection and the DAO for reading and writing Policy Framework concepts
78     private PfDao pfDao;
79
80     /**
81      * Constructor that takes the parameters.
82      *
83      * @param parameters the parameters for the provider
84      */
85     public DatabasePolicyModelsProviderImpl(@NonNull final PolicyModelsProviderParameters parameters) {
86         this.parameters = parameters;
87     }
88
89     @Override
90     public void init() throws PfModelException {
91         LOGGER.debug("opening the database connection to {} using persistence unit {}", parameters.getDatabaseUrl(),
92                 parameters.getPersistenceUnit());
93
94         if (pfDao != null) {
95             String errorMessage = "provider is already initialized";
96             LOGGER.warn(errorMessage);
97             throw new PfModelException(Response.Status.NOT_ACCEPTABLE, errorMessage);
98         }
99
100         // Parameters for the DAO
101         final DaoParameters daoParameters = new DaoParameters();
102         daoParameters.setPluginClass(DefaultPfDao.class.getName());
103         daoParameters.setPersistenceUnit(parameters.getPersistenceUnit());
104
105         // Decode the password using Base64
106         String decodedPassword = new String(Base64.getDecoder().decode(getValue(parameters.getDatabasePassword())));
107
108         // @formatter:off
109         Properties jdbcProperties = new Properties();
110         jdbcProperties.setProperty(PersistenceUnitProperties.JDBC_DRIVER,   parameters.getDatabaseDriver());
111         jdbcProperties.setProperty(PersistenceUnitProperties.JDBC_URL,      parameters.getDatabaseUrl());
112         jdbcProperties.setProperty(PersistenceUnitProperties.JDBC_USER,     parameters.getDatabaseUser());
113         jdbcProperties.setProperty(PersistenceUnitProperties.JDBC_PASSWORD, decodedPassword);
114         // @formatter:on
115
116         daoParameters.setJdbcProperties(jdbcProperties);
117
118         try {
119             pfDao = new PfDaoFactory().createPfDao(daoParameters);
120             pfDao.init(daoParameters);
121         } catch (Exception exc) {
122             String errorMessage = "could not create Data Access Object (DAO) using url \"" + parameters.getDatabaseUrl()
123                     + "\" and persistence unit \"" + parameters.getPersistenceUnit() + "\"";
124
125             this.close();
126             throw new PfModelException(Response.Status.NOT_ACCEPTABLE, errorMessage, exc);
127         }
128     }
129
130     private String getValue(final String value) {
131         if (value != null && value.matches("[$][{].*[}]$")) {
132             return System.getenv(value.substring(2, value.length() - 1));
133         }
134         return value;
135     }
136
137     @Override
138     public void close() throws PfModelException {
139         LOGGER.debug("closing the database connection to {} using persistence unit {}", parameters.getDatabaseUrl(),
140                 parameters.getPersistenceUnit());
141
142         if (pfDao != null) {
143             pfDao.close();
144             pfDao = null;
145         }
146
147         LOGGER.debug("closed the database connection to {} using persistence unit {}", parameters.getDatabaseUrl(),
148                 parameters.getPersistenceUnit());
149     }
150
151     @Override
152     public ToscaServiceTemplate getPolicyTypes(final String name, final String version) throws PfModelException {
153         assertInitialized();
154         return new AuthorativeToscaProvider().getPolicyTypes(pfDao, name, version);
155     }
156
157     @Override
158     public List<ToscaPolicyType> getPolicyTypeList(final String name, final String version) throws PfModelException {
159         assertInitialized();
160         return new AuthorativeToscaProvider().getPolicyTypeList(pfDao, name, version);
161     }
162
163     @Override
164     public ToscaServiceTemplate getFilteredPolicyTypes(@NonNull ToscaPolicyTypeFilter filter) throws PfModelException {
165         assertInitialized();
166         return new AuthorativeToscaProvider().getFilteredPolicyTypes(pfDao, filter);
167     }
168
169     @Override
170     public List<ToscaPolicyType> getFilteredPolicyTypeList(@NonNull ToscaPolicyTypeFilter filter)
171             throws PfModelException {
172         assertInitialized();
173         return new AuthorativeToscaProvider().getFilteredPolicyTypeList(pfDao, filter);
174     }
175
176     @Override
177     public ToscaServiceTemplate createPolicyTypes(@NonNull final ToscaServiceTemplate serviceTemplate)
178             throws PfModelException {
179         assertInitialized();
180         return new AuthorativeToscaProvider().createPolicyTypes(pfDao, serviceTemplate);
181     }
182
183     @Override
184     public ToscaServiceTemplate updatePolicyTypes(@NonNull final ToscaServiceTemplate serviceTemplate)
185             throws PfModelException {
186         assertInitialized();
187         return new AuthorativeToscaProvider().updatePolicyTypes(pfDao, serviceTemplate);
188     }
189
190     @Override
191     public ToscaServiceTemplate deletePolicyType(@NonNull final String name, @NonNull final String version)
192             throws PfModelException {
193         assertInitialized();
194
195         ToscaPolicyTypeIdentifier policyTypeIdentifier = new ToscaPolicyTypeIdentifier(name, version);
196         assertPolicyTypeNotSupportedInPdpGroup(policyTypeIdentifier);
197
198         return new AuthorativeToscaProvider().deletePolicyType(pfDao, name, version);
199     }
200
201     @Override
202     public ToscaServiceTemplate getPolicies(final String name, final String version) throws PfModelException {
203         assertInitialized();
204         return new AuthorativeToscaProvider().getPolicies(pfDao, name, version);
205     }
206
207     @Override
208     public List<ToscaPolicy> getPolicyList(final String name, final String version) throws PfModelException {
209         assertInitialized();
210         return new AuthorativeToscaProvider().getPolicyList(pfDao, name, version);
211     }
212
213     @Override
214     public ToscaServiceTemplate getFilteredPolicies(@NonNull ToscaPolicyFilter filter) throws PfModelException {
215         assertInitialized();
216         return new AuthorativeToscaProvider().getFilteredPolicies(pfDao, filter);
217     }
218
219     @Override
220     public List<ToscaPolicy> getFilteredPolicyList(@NonNull ToscaPolicyFilter filter) throws PfModelException {
221         assertInitialized();
222         return new AuthorativeToscaProvider().getFilteredPolicyList(pfDao, filter);
223     }
224
225     @Override
226     public ToscaServiceTemplate createPolicies(@NonNull final ToscaServiceTemplate serviceTemplate)
227             throws PfModelException {
228         assertInitialized();
229         return new AuthorativeToscaProvider().createPolicies(pfDao, serviceTemplate);
230     }
231
232     @Override
233     public ToscaServiceTemplate updatePolicies(@NonNull final ToscaServiceTemplate serviceTemplate)
234             throws PfModelException {
235         assertInitialized();
236         return new AuthorativeToscaProvider().updatePolicies(pfDao, serviceTemplate);
237     }
238
239     @Override
240     public ToscaServiceTemplate deletePolicy(@NonNull final String name, @NonNull final String version)
241             throws PfModelException {
242         assertInitialized();
243
244         ToscaPolicyIdentifier policyIdentifier = new ToscaPolicyIdentifier(name, version);
245         assertPolicyNotDeployedInPdpGroup(policyIdentifier);
246
247         return new AuthorativeToscaProvider().deletePolicy(pfDao, name, version);
248     }
249
250     @Override
251     public LegacyOperationalPolicy getOperationalPolicy(@NonNull final String policyId, final String policyVersion)
252             throws PfModelException {
253         assertInitialized();
254         return new LegacyProvider().getOperationalPolicy(pfDao, policyId, policyVersion);
255     }
256
257     @Override
258     public LegacyOperationalPolicy createOperationalPolicy(
259             @NonNull final LegacyOperationalPolicy legacyOperationalPolicy) throws PfModelException {
260         assertInitialized();
261         return new LegacyProvider().createOperationalPolicy(pfDao, legacyOperationalPolicy);
262     }
263
264     @Override
265     public LegacyOperationalPolicy updateOperationalPolicy(
266             @NonNull final LegacyOperationalPolicy legacyOperationalPolicy) throws PfModelException {
267         assertInitialized();
268         return new LegacyProvider().updateOperationalPolicy(pfDao, legacyOperationalPolicy);
269     }
270
271     @Override
272     public LegacyOperationalPolicy deleteOperationalPolicy(@NonNull final String policyId,
273             @NonNull final String policyVersion) throws PfModelException {
274         assertInitialized();
275
276         assertPolicyNotDeployedInPdpGroup(
277                 new ToscaPolicyIdentifier(policyId, policyVersion + LegacyProvider.LEGACY_MINOR_PATCH_SUFFIX));
278
279         return new LegacyProvider().deleteOperationalPolicy(pfDao, policyId, policyVersion);
280     }
281
282     @Override
283     public Map<String, LegacyGuardPolicyOutput> getGuardPolicy(@NonNull final String policyId,
284             final String policyVersion) throws PfModelException {
285         assertInitialized();
286         return new LegacyProvider().getGuardPolicy(pfDao, policyId, policyVersion);
287     }
288
289     @Override
290     public Map<String, LegacyGuardPolicyOutput>
291             createGuardPolicy(@NonNull final LegacyGuardPolicyInput legacyGuardPolicy) throws PfModelException {
292         assertInitialized();
293         return new LegacyProvider().createGuardPolicy(pfDao, legacyGuardPolicy);
294     }
295
296     @Override
297     public Map<String, LegacyGuardPolicyOutput>
298             updateGuardPolicy(@NonNull final LegacyGuardPolicyInput legacyGuardPolicy) throws PfModelException {
299         assertInitialized();
300         return new LegacyProvider().updateGuardPolicy(pfDao, legacyGuardPolicy);
301     }
302
303     @Override
304     public Map<String, LegacyGuardPolicyOutput> deleteGuardPolicy(@NonNull final String policyId,
305             @NonNull final String policyVersion) throws PfModelException {
306         assertInitialized();
307
308         assertPolicyNotDeployedInPdpGroup(
309                 new ToscaPolicyIdentifier(policyId, policyVersion + LegacyProvider.LEGACY_MINOR_PATCH_SUFFIX));
310
311         return new LegacyProvider().deleteGuardPolicy(pfDao, policyId, policyVersion);
312     }
313
314     @Override
315     public List<PdpGroup> getPdpGroups(final String name) throws PfModelException {
316         assertInitialized();
317         return new PdpProvider().getPdpGroups(pfDao, name);
318     }
319
320     @Override
321     public List<PdpGroup> getFilteredPdpGroups(@NonNull PdpGroupFilter filter) throws PfModelException {
322         assertInitialized();
323         return new PdpProvider().getFilteredPdpGroups(pfDao, filter);
324     }
325
326     @Override
327     public List<PdpGroup> createPdpGroups(@NonNull final List<PdpGroup> pdpGroups) throws PfModelException {
328         assertInitialized();
329         return new PdpProvider().createPdpGroups(pfDao, pdpGroups);
330     }
331
332     @Override
333     public List<PdpGroup> updatePdpGroups(@NonNull final List<PdpGroup> pdpGroups) throws PfModelException {
334         assertInitialized();
335         return new PdpProvider().updatePdpGroups(pfDao, pdpGroups);
336     }
337
338     @Override
339     public void updatePdpSubGroup(@NonNull final String pdpGroupName, @NonNull final PdpSubGroup pdpSubGroup)
340             throws PfModelException {
341         assertInitialized();
342         new PdpProvider().updatePdpSubGroup(pfDao, pdpGroupName, pdpSubGroup);
343     }
344
345     @Override
346     public void updatePdp(@NonNull String pdpGroupName, @NonNull String pdpSubGroup, @NonNull Pdp pdp)
347             throws PfModelException {
348         new PdpProvider().updatePdp(pfDao, pdpGroupName, pdpSubGroup, pdp);
349     }
350
351     @Override
352     public PdpGroup deletePdpGroup(@NonNull final String name) throws PfModelException {
353         assertInitialized();
354         return new PdpProvider().deletePdpGroup(pfDao, name);
355     }
356
357     @Override
358     public List<PdpStatistics> getPdpStatistics(final String name, final Date timestamp) throws PfModelException {
359         assertInitialized();
360         return new PdpStatisticsProvider().getPdpStatistics(pfDao, name, timestamp);
361     }
362
363     @Override
364     public List<PdpStatistics> getFilteredPdpStatistics(final String name, @NonNull final String pdpGroupName,
365             final String pdpSubGroup, final Date startTimeStamp, final Date endTimeStamp, final String sortOrder,
366             final int getRecordNum) throws PfModelException {
367         assertInitialized();
368         return new PdpStatisticsProvider().getFilteredPdpStatistics(pfDao, name, pdpGroupName, pdpSubGroup,
369                 startTimeStamp, endTimeStamp, sortOrder, getRecordNum);
370     }
371
372     @Override
373     public List<PdpStatistics> createPdpStatistics(@NonNull final List<PdpStatistics> pdpStatisticsList)
374             throws PfModelException {
375         assertInitialized();
376         return new PdpStatisticsProvider().createPdpStatistics(pfDao, pdpStatisticsList);
377     }
378
379     @Override
380     public List<PdpStatistics> updatePdpStatistics(@NonNull final List<PdpStatistics> pdpStatisticsList)
381             throws PfModelException {
382         assertInitialized();
383         return new PdpStatisticsProvider().updatePdpStatistics(pfDao, pdpStatisticsList);
384     }
385
386     @Override
387     public List<PdpStatistics> deletePdpStatistics(@NonNull final String name, final Date timestamp)
388             throws PfModelException {
389         assertInitialized();
390         return new PdpStatisticsProvider().deletePdpStatistics(pfDao, name, timestamp);
391     }
392
393     /**
394      * Check if the model provider is initialized.
395      */
396     private void assertInitialized() {
397         if (pfDao == null) {
398             String errorMessage = "policy models provider is not initilaized";
399             LOGGER.warn(errorMessage);
400             throw new PfModelRuntimeException(Response.Status.BAD_REQUEST, errorMessage);
401         }
402     }
403
404     /**
405      * Assert that the policy type is not supported in any PDP group.
406      *
407      * @param policyTypeIdentifier the policy type identifier
408      * @throws PfModelException if the policy type is supported in a PDP group
409      */
410     private void assertPolicyTypeNotSupportedInPdpGroup(ToscaPolicyTypeIdentifier policyTypeIdentifier)
411             throws PfModelException {
412         for (PdpGroup pdpGroup : getPdpGroups(null)) {
413             for (PdpSubGroup pdpSubGroup : pdpGroup.getPdpSubgroups()) {
414                 if (pdpSubGroup.getSupportedPolicyTypes().contains(policyTypeIdentifier)) {
415                     throw new PfModelRuntimeException(Response.Status.NOT_ACCEPTABLE,
416                             "policy type is in use, it is referenced in PDP group " + pdpGroup.getName() + " subgroup "
417                                     + pdpSubGroup.getPdpType());
418                 }
419             }
420         }
421     }
422
423     /**
424      * Assert that the policy is not deployed in a PDP group.
425      *
426      * @param policyIdentifier the identifier of the policy
427      * @throws PfModelException thrown if the policy is deployed in a PDP group
428      */
429     private void assertPolicyNotDeployedInPdpGroup(final ToscaPolicyIdentifier policyIdentifier)
430             throws PfModelException {
431         for (PdpGroup pdpGroup : getPdpGroups(null)) {
432             for (PdpSubGroup pdpSubGroup : pdpGroup.getPdpSubgroups()) {
433                 if (pdpSubGroup.getPolicies().contains(policyIdentifier)) {
434                     throw new PfModelRuntimeException(Response.Status.NOT_ACCEPTABLE,
435                             "policy is in use, it is deployed in PDP group " + pdpGroup.getName() + " subgroup "
436                                     + pdpSubGroup.getPdpType());
437                 }
438             }
439         }
440     }
441 }