2 * ============LICENSE_START=======================================================
4 * ================================================================================
5 * Copyright (C) 2019-2021 AT&T Intellectual Property. All rights reserved.
6 * Modifications Copyright (C) 2019-2021, 2023 Nordix Foundation.
7 * ================================================================================
8 * Licensed under the Apache License, Version 2.0 (the "License");
9 * you may not use this file except in compliance with the License.
10 * You may obtain a copy of the License at
12 * http://www.apache.org/licenses/LICENSE-2.0
14 * Unless required by applicable law or agreed to in writing, software
15 * distributed under the License is distributed on an "AS IS" BASIS,
16 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17 * See the License for the specific language governing permissions and
18 * limitations under the License.
20 * SPDX-License-Identifier: Apache-2.0
21 * ============LICENSE_END=========================================================
24 package org.onap.policy.models.pdp.persistence.concepts;
26 import jakarta.persistence.CascadeType;
27 import jakarta.persistence.Column;
28 import jakarta.persistence.ElementCollection;
29 import jakarta.persistence.EmbeddedId;
30 import jakarta.persistence.Entity;
31 import jakarta.persistence.FetchType;
32 import jakarta.persistence.Inheritance;
33 import jakarta.persistence.InheritanceType;
34 import jakarta.persistence.JoinColumn;
35 import jakarta.persistence.JoinTable;
36 import jakarta.persistence.OneToMany;
37 import jakarta.persistence.Table;
38 import java.io.Serial;
39 import java.util.ArrayList;
40 import java.util.LinkedHashMap;
41 import java.util.List;
43 import java.util.Map.Entry;
45 import lombok.EqualsAndHashCode;
46 import lombok.NonNull;
47 import org.onap.policy.common.parameters.BeanValidationResult;
48 import org.onap.policy.common.parameters.annotations.Min;
49 import org.onap.policy.common.parameters.annotations.NotBlank;
50 import org.onap.policy.common.parameters.annotations.NotNull;
51 import org.onap.policy.common.parameters.annotations.Valid;
52 import org.onap.policy.models.base.PfAuthorative;
53 import org.onap.policy.models.base.PfConcept;
54 import org.onap.policy.models.base.PfConceptKey;
55 import org.onap.policy.models.base.PfKey;
56 import org.onap.policy.models.base.PfKeyUse;
57 import org.onap.policy.models.base.PfReferenceKey;
58 import org.onap.policy.models.base.PfSearchableKey;
59 import org.onap.policy.models.base.PfUtils;
60 import org.onap.policy.models.base.validation.annotations.VerifyKey;
61 import org.onap.policy.models.pdp.concepts.Pdp;
62 import org.onap.policy.models.pdp.concepts.PdpSubGroup;
63 import org.onap.policy.models.tosca.authorative.concepts.ToscaConceptIdentifier;
66 * Class to represent a PDP subgroup in the database.
68 * @author Liam Fallon (liam.fallon@est.tech)
71 @Table(name = "PdpSubGroup")
72 @Inheritance(strategy = InheritanceType.TABLE_PER_CLASS)
74 @EqualsAndHashCode(callSuper = false)
75 public class JpaPdpSubGroup extends PfConcept implements PfAuthorative<PdpSubGroup> {
77 private static final long serialVersionUID = -357224425637789775L;
82 private PfReferenceKey key;
86 private List<@NotNull @Valid PfSearchableKey> supportedPolicyTypes;
90 private List<PfConceptKey> policies;
94 private int currentInstanceCount;
98 private int desiredInstanceCount;
101 private Map<@NotNull @NotBlank String, @NotNull @NotBlank String> properties;
104 @OneToMany(fetch = FetchType.EAGER, cascade = CascadeType.ALL, orphanRemoval = true)
107 @JoinColumn(name = "pdpParentKeyName", referencedColumnName = "parentKeyName"),
108 @JoinColumn(name = "pdpParentKeyVersion", referencedColumnName = "parentKeyVersion"),
109 @JoinColumn(name = "pdpParentLocalName", referencedColumnName = "parentLocalName"),
110 @JoinColumn(name = "pdpLocalName", referencedColumnName = "localName")
115 private List<@NotNull @Valid JpaPdp> pdpInstances;
118 * The Default Constructor creates a {@link JpaPdpSubGroup} object with a null key.
120 public JpaPdpSubGroup() {
121 this(new PfReferenceKey());
125 * The Key Constructor creates a {@link JpaPdpSubGroup} object with the given concept key.
129 public JpaPdpSubGroup(@NonNull final PfReferenceKey key) {
130 this(key, new ArrayList<>(), new ArrayList<>(), new ArrayList<>());
134 * The Key Constructor creates a {@link JpaPdpSubGroup} object with all mandatory fields.
137 * @param supportedPolicyTypes Supported policy types
138 * @param policies policies deployed on this PDP subgroups
139 * @param pdpInstances the PDP instances on this PDP subgroups
141 public JpaPdpSubGroup(@NonNull final PfReferenceKey key, @NonNull final List<PfSearchableKey> supportedPolicyTypes,
142 @NonNull List<PfConceptKey> policies, @NonNull final List<JpaPdp> pdpInstances) {
144 this.supportedPolicyTypes = supportedPolicyTypes;
145 this.policies = policies;
146 this.pdpInstances = pdpInstances;
152 * @param copyConcept the concept to copy from
154 public JpaPdpSubGroup(@NonNull final JpaPdpSubGroup copyConcept) {
156 this.key = new PfReferenceKey(copyConcept.key);
157 this.supportedPolicyTypes = PfUtils.mapList(copyConcept.supportedPolicyTypes,
158 PfSearchableKey::new, new ArrayList<>(0));
159 this.policies = PfUtils.mapList(copyConcept.policies, PfConceptKey::new, new ArrayList<>(0));
160 this.currentInstanceCount = copyConcept.currentInstanceCount;
161 this.desiredInstanceCount = copyConcept.desiredInstanceCount;
162 this.properties = (copyConcept.properties != null ? new LinkedHashMap<>(copyConcept.properties) : null);
163 this.pdpInstances = PfUtils.mapList(copyConcept.pdpInstances, JpaPdp::new, new ArrayList<>(0));
167 * Authorative constructor.
169 * @param authorativeConcept the authorative concept to copy from
171 public JpaPdpSubGroup(@NonNull final PdpSubGroup authorativeConcept) {
172 this.fromAuthorative(authorativeConcept);
176 public PdpSubGroup toAuthorative() {
177 var pdpSubgroup = new PdpSubGroup();
179 pdpSubgroup.setPdpType(getKey().getLocalName());
181 pdpSubgroup.setSupportedPolicyTypes(new ArrayList<>());
182 for (PfSearchableKey supportedPolicyTypeKey : supportedPolicyTypes) {
183 var supportedPolicyTypeIdent = new ToscaConceptIdentifier(
184 supportedPolicyTypeKey.getName(), supportedPolicyTypeKey.getVersion());
185 pdpSubgroup.getSupportedPolicyTypes().add(supportedPolicyTypeIdent);
188 pdpSubgroup.setPolicies(new ArrayList<>());
189 for (PfConceptKey policyKey : policies) {
190 var toscaPolicyIdentifier = new ToscaConceptIdentifier();
191 toscaPolicyIdentifier.setName(policyKey.getName());
192 toscaPolicyIdentifier.setVersion(policyKey.getVersion());
193 pdpSubgroup.getPolicies().add(toscaPolicyIdentifier);
196 pdpSubgroup.setCurrentInstanceCount(currentInstanceCount);
197 pdpSubgroup.setDesiredInstanceCount(desiredInstanceCount);
198 pdpSubgroup.setProperties(properties == null ? null : new LinkedHashMap<>(properties));
200 pdpSubgroup.setPdpInstances(new ArrayList<>());
201 for (JpaPdp jpaPdp : pdpInstances) {
202 pdpSubgroup.getPdpInstances().add(jpaPdp.toAuthorative());
209 public void fromAuthorative(@NonNull final PdpSubGroup pdpSubgroup) {
210 if (this.key == null || this.getKey().isNullKey()) {
211 this.setKey(new PfReferenceKey());
212 getKey().setLocalName(pdpSubgroup.getPdpType());
215 this.supportedPolicyTypes = new ArrayList<>();
216 if (pdpSubgroup.getSupportedPolicyTypes() != null) {
217 for (ToscaConceptIdentifier supportedPolicyType : pdpSubgroup.getSupportedPolicyTypes()) {
218 this.supportedPolicyTypes
219 .add(new PfSearchableKey(supportedPolicyType.getName(), supportedPolicyType.getVersion()));
223 this.policies = new ArrayList<>();
224 if (pdpSubgroup.getPolicies() != null) {
225 for (ToscaConceptIdentifier toscaPolicyIdentifier : pdpSubgroup.getPolicies()) {
227 .add(new PfConceptKey(toscaPolicyIdentifier.getName(), toscaPolicyIdentifier.getVersion()));
230 this.currentInstanceCount = pdpSubgroup.getCurrentInstanceCount();
231 this.desiredInstanceCount = pdpSubgroup.getDesiredInstanceCount();
233 (pdpSubgroup.getProperties() == null ? null : new LinkedHashMap<>(pdpSubgroup.getProperties()));
235 this.pdpInstances = new ArrayList<>();
236 if (pdpSubgroup.getPdpInstances() != null) {
237 for (Pdp pdp : pdpSubgroup.getPdpInstances()) {
238 var jpaPdp = new JpaPdp();
239 jpaPdp.setKey(new PfReferenceKey(getKey(), pdp.getInstanceId()));
240 jpaPdp.fromAuthorative(pdp);
241 this.pdpInstances.add(jpaPdp);
247 public List<PfKey> getKeys() {
248 List<PfKey> keyList = getKey().getKeys();
250 for (PfSearchableKey ptkey : supportedPolicyTypes) {
251 keyList.add(new PfKeyUse(ptkey));
254 for (PfConceptKey pkey : policies) {
255 keyList.add(new PfKeyUse(pkey));
258 for (JpaPdp jpaPdp : pdpInstances) {
259 keyList.addAll(jpaPdp.getKeys());
267 public void clean() {
270 for (PfSearchableKey ptkey : supportedPolicyTypes) {
274 for (PfConceptKey pkey : policies) {
278 if (properties != null) {
279 Map<String, String> cleanedPropertyMap = new LinkedHashMap<>();
280 for (Entry<String, String> propertyEntry : properties.entrySet()) {
281 cleanedPropertyMap.put(propertyEntry.getKey().trim(), propertyEntry.getValue().trim());
283 properties = cleanedPropertyMap;
286 for (JpaPdp jpaPdp : pdpInstances) {
292 public BeanValidationResult validate(@NonNull String fieldName) {
293 BeanValidationResult result = super.validate(fieldName);
295 validateKeyNotNull(result, "parent of key", key.getParentConceptKey());
297 if (supportedPolicyTypes != null && supportedPolicyTypes.isEmpty()) {
298 addResult(result, "supportedPolicyTypes", supportedPolicyTypes, "is empty");
305 public int compareTo(final PfConcept otherConcept) {
306 if (otherConcept == null) {
309 if (this == otherConcept) {
312 if (getClass() != otherConcept.getClass()) {
313 return getClass().getName().compareTo(otherConcept.getClass().getName());
316 final JpaPdpSubGroup other = (JpaPdpSubGroup) otherConcept;
317 if (!key.equals(other.key)) {
318 return key.compareTo(other.key);
321 int result = PfUtils.compareObjects(supportedPolicyTypes, other.supportedPolicyTypes);
326 result = PfUtils.compareObjects(policies, other.policies);
331 if (currentInstanceCount != other.currentInstanceCount) {
332 return currentInstanceCount - other.currentInstanceCount;
335 if (desiredInstanceCount != other.desiredInstanceCount) {
336 return desiredInstanceCount - other.desiredInstanceCount;
339 result = PfUtils.compareObjects(properties, other.properties);
344 return PfUtils.compareObjects(pdpInstances, other.pdpInstances);