From 4c28d2cdbf03be9dfe51caa05d45ba341b4c94cd Mon Sep 17 00:00:00 2001 From: liamfallon Date: Thu, 14 Mar 2019 10:01:58 +0000 Subject: Add DAO Enabled Tosca Model Add DAO annotations to TOSCA model Add keying between concepts and define foreign keys in objects for translation to DB schema Added provider interface, factory, and stubbed implementation. Completed unit test for models-base Completed unit test for models-dao Completed unit test for models-tosca Issue-ID: POLICY-1195 Change-Id: I53a0ba8b7a679b6887b38bdab184b60315e0cf5b Signed-off-by: liamfallon --- .../org/onap/policy/models/base/PfConcept.java | 28 +-- .../policy/models/base/PfConceptContainer.java | 268 +++++++++++++++++++++ .../org/onap/policy/models/base/PfConceptKey.java | 20 +- .../java/org/onap/policy/models/base/PfKey.java | 13 +- .../java/org/onap/policy/models/base/PfKeyUse.java | 84 ++++--- .../java/org/onap/policy/models/base/PfModel.java | 73 +++--- .../onap/policy/models/base/PfModelException.java | 38 +-- .../models/base/PfModelRuntimeException.java | 38 +-- .../onap/policy/models/base/PfModelService.java | 36 +-- .../onap/policy/models/base/PfReferenceKey.java | 5 + .../java/org/onap/policy/models/base/PfUtils.java | 59 +++++ .../policy/models/base/PfValidationResult.java | 23 +- 12 files changed, 506 insertions(+), 179 deletions(-) create mode 100644 models-base/src/main/java/org/onap/policy/models/base/PfConceptContainer.java create mode 100644 models-base/src/main/java/org/onap/policy/models/base/PfUtils.java (limited to 'models-base/src/main/java') diff --git a/models-base/src/main/java/org/onap/policy/models/base/PfConcept.java b/models-base/src/main/java/org/onap/policy/models/base/PfConcept.java index b74b0374d..c41b0de56 100644 --- a/models-base/src/main/java/org/onap/policy/models/base/PfConcept.java +++ b/models-base/src/main/java/org/onap/policy/models/base/PfConcept.java @@ -23,7 +23,7 @@ package org.onap.policy.models.base; import java.io.Serializable; import java.util.List; -import org.onap.policy.common.utils.validation.Assertions; +import lombok.NonNull; /** * This class is the base class for all Policy Framework concept classes. It enforces implementation @@ -43,8 +43,7 @@ public abstract class PfConcept implements Serializable, Comparable { * * @param copyConcept the concept to copy from */ - public PfConcept(final PfConcept copyConcept) { - Assertions.argumentNotNull(copyConcept, "copy concept may not be null"); + public PfConcept(@NonNull final PfConcept copyConcept) { copyConcept.copyTo(this); } @@ -70,7 +69,7 @@ public abstract class PfConcept implements Serializable, Comparable { * @return the validation result that was passed in in the @{link result} field with the result * of this validation added */ - public abstract PfValidationResult validate(PfValidationResult result); + public abstract PfValidationResult validate(@NonNull final PfValidationResult result); /** * Clean this concept, tidy up any superfluous information such as leading and trailing white @@ -78,27 +77,12 @@ public abstract class PfConcept implements Serializable, Comparable { */ public abstract void clean(); - /* - * (non-Javadoc) - * - * @see java.lang.Object#equals(java.lang.Object) - */ @Override public abstract boolean equals(Object otherObject); - /* - * (non-Javadoc) - * - * @see java.lang.Object#toString() - */ @Override public abstract String toString(); - /* - * (non-Javadoc) - * - * @see java.lang.Object#hashCode() - */ @Override public abstract int hashCode(); @@ -109,7 +93,7 @@ public abstract class PfConcept implements Serializable, Comparable { * @param target the target object to which this object is copied * @return the copied object */ - public abstract PfConcept copyTo(PfConcept target); + public abstract PfConcept copyTo(@NonNull PfConcept target); /** * Gets the ID string of this concept. @@ -126,9 +110,7 @@ public abstract class PfConcept implements Serializable, Comparable { * @param id the key ID to match against * @return true, if this key matches the ID */ - public final boolean matchesId(final String id) { - Assertions.argumentNotNull(id, "id may not be null"); - + public final boolean matchesId(@NonNull final String id) { // Check the ID return getId().equals(id); } diff --git a/models-base/src/main/java/org/onap/policy/models/base/PfConceptContainer.java b/models-base/src/main/java/org/onap/policy/models/base/PfConceptContainer.java new file mode 100644 index 000000000..46094610a --- /dev/null +++ b/models-base/src/main/java/org/onap/policy/models/base/PfConceptContainer.java @@ -0,0 +1,268 @@ +/*- + * ============LICENSE_START======================================================= + * Copyright (C) 2019 Nordix Foundation. + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * SPDX-License-Identifier: Apache-2.0 + * ============LICENSE_END========================================================= + */ + +package org.onap.policy.models.base; + +import java.util.List; +import java.util.Map; +import java.util.Map.Entry; +import java.util.NavigableMap; +import java.util.Set; +import java.util.TreeMap; + +import javax.persistence.CascadeType; +import javax.persistence.EmbeddedId; +import javax.persistence.Entity; +import javax.persistence.ManyToMany; +import javax.persistence.Table; +import javax.ws.rs.core.Response; + +import lombok.Data; +import lombok.EqualsAndHashCode; +import lombok.NonNull; + +import org.onap.policy.common.utils.validation.Assertions; +import org.onap.policy.models.base.PfValidationResult.ValidationResult; + +/** + * This class is a concept container and holds a map of concepts. The {@link PfConceptContainer} + * class implements the helper methods of the {@link PfConceptGetter} interface to allow + * {@link PfConceptContainer} instances to be retrieved by calling methods directly on this class + * without referencing the contained map. + * + *

Validation checks that the container key is not null. An error is issued if no concepts are + * defined in the container. Each concept entry is checked to ensure that its key and value are not + * null and that the key matches the key in the map value. Each concept entry is then validated + * individually. + * + * @param C the concept being contained + */ +@Entity +@Table(name = "PfConceptContainer") +@Data +@EqualsAndHashCode(callSuper = false) + +public class PfConceptContainer extends PfConcept implements PfConceptGetter { + private static final long serialVersionUID = -324211738823208318L; + + @EmbeddedId + private PfConceptKey key; + + @ManyToMany(cascade = CascadeType.ALL) + private Map conceptMap; + + /** + * The Default Constructor creates a {@link PfConceptContainer} object with a null artifact key + * and creates an empty concept map. + */ + public PfConceptContainer() { + this(new PfConceptKey()); + } + + /** + * The Key Constructor creates a {@link PfConceptContainer} object with the given artifact key + * and creates an empty concept map. + * + * @param key the concept key + */ + public PfConceptContainer(@NonNull final PfConceptKey key) { + this(key, new TreeMap()); + } + + /** + * This Constructor creates an concept container with all of its fields defined. + * + * @param key the concept container key + * @param conceptMap the concepts to be stored in the concept container + */ + public PfConceptContainer(@NonNull final PfConceptKey key, @NonNull final Map conceptMap) { + super(); + + this.key = key; + this.conceptMap = new TreeMap<>(conceptMap); + } + + /** + * Copy constructor. + * + * @param copyConcept the concept to copy from + */ + public PfConceptContainer(@NonNull final PfConceptContainer copyConcept) { + super(copyConcept); + } + + @Override + public List getKeys() { + final List keyList = key.getKeys(); + + for (final C concept : conceptMap.values()) { + keyList.addAll(concept.getKeys()); + } + + return keyList; + } + + @Override + public void clean() { + key.clean(); + for (final Entry conceptEntry : conceptMap.entrySet()) { + conceptEntry.getKey().clean(); + conceptEntry.getValue().clean(); + } + } + + @Override + public PfValidationResult validate(@NonNull final PfValidationResult resultIn) { + PfValidationResult result = resultIn; + + if (key.equals(PfConceptKey.getNullKey())) { + result.addValidationMessage( + new PfValidationMessage(key, this.getClass(), ValidationResult.INVALID, "key is a null key")); + } + + result = key.validate(result); + + if (conceptMap.isEmpty()) { + result.addValidationMessage(new PfValidationMessage(key, this.getClass(), ValidationResult.INVALID, + "conceptMap may not be empty")); + } else { + result = validateConceptMap(result); + } + + return result; + } + + /** + * Validate the concept map of the container. + * + * @param resultIn the incoming validation results so far + * @return the validation results with the results of this validation added + */ + private PfValidationResult validateConceptMap(final PfValidationResult resultIn) { + PfValidationResult result = resultIn; + + for (final Entry conceptEntry : conceptMap.entrySet()) { + if (conceptEntry.getKey().equals(PfConceptKey.getNullKey())) { + result.addValidationMessage(new PfValidationMessage(key, this.getClass(), ValidationResult.INVALID, + "key on concept entry " + conceptEntry.getKey() + " may not be the null key")); + } else if (conceptEntry.getValue() == null) { + result.addValidationMessage(new PfValidationMessage(key, this.getClass(), ValidationResult.INVALID, + "value on concept entry " + conceptEntry.getKey() + " may not be null")); + } else if (!conceptEntry.getKey().equals(conceptEntry.getValue().getKey())) { + result.addValidationMessage(new PfValidationMessage(key, this.getClass(), + ValidationResult.INVALID, "key on concept entry key " + conceptEntry.getKey() + + " does not equal concept value key " + conceptEntry.getValue().getKey())); + result = conceptEntry.getValue().validate(result); + } else { + result = conceptEntry.getValue().validate(result); + } + } + return result; + } + + @Override + public int compareTo(final PfConcept otherConcept) { + if (otherConcept == null) { + return -1; + } + if (this == otherConcept) { + return 0; + } + if (getClass() != otherConcept.getClass()) { + return this.hashCode() - otherConcept.hashCode(); + } + + @SuppressWarnings("unchecked") + final PfConceptContainer other = (PfConceptContainer) otherConcept; + int retVal = key.compareTo(other.key); + if (retVal != 0) { + return retVal; + } + + if (!conceptMap.equals(other.conceptMap)) { + return (conceptMap.hashCode() - other.conceptMap.hashCode()); + } + + return 0; + } + + @Override + public PfConcept copyTo(@NonNull final PfConcept target) { + Assertions.instanceOf(target, PfConceptContainer.class); + + @SuppressWarnings("unchecked") + final PfConceptContainer copy = (PfConceptContainer) target; + copy.setKey(new PfConceptKey(key)); + final Map newConceptMap = new TreeMap<>(); + for (final Entry conceptMapEntry : conceptMap.entrySet()) { + newConceptMap.put(new PfConceptKey(conceptMapEntry.getKey()), + new ConceptCloner().cloneConcept(conceptMapEntry.getValue())); + } + copy.setConceptMap(newConceptMap); + + return copy; + } + + @Override + public C get(final PfConceptKey conceptKey) { + return new PfConceptGetterImpl<>((NavigableMap) conceptMap).get(conceptKey); + } + + @Override + public C get(final String conceptKeyName) { + return new PfConceptGetterImpl<>((NavigableMap) conceptMap).get(conceptKeyName); + } + + @Override + public C get(final String conceptKeyName, final String conceptKeyVersion) { + return new PfConceptGetterImpl<>((NavigableMap) conceptMap).get(conceptKeyName, + conceptKeyVersion); + } + + @Override + public Set getAll(final String conceptKeyName) { + return new PfConceptGetterImpl<>((NavigableMap) conceptMap).getAll(conceptKeyName); + } + + @Override + public Set getAll(final String conceptKeyName, final String conceptKeyVersion) { + return new PfConceptGetterImpl<>((NavigableMap) conceptMap).getAll(conceptKeyName, + conceptKeyVersion); + } + + /** + * Private inner class that returns a clone of a concept by calling the copy constructor on the + * original class. + */ + private class ConceptCloner { + @SuppressWarnings("unchecked") + public C cloneConcept(final C originalConcept) { + try { + C clonedConcept = (C) originalConcept.getClass().newInstance(); + originalConcept.copyTo(clonedConcept); + return clonedConcept; + } catch (Exception ex) { + throw new PfModelRuntimeException(Response.Status.INTERNAL_SERVER_ERROR, + "Failed to create a clone of class \"" + originalConcept.getClass().getCanonicalName() + "\"", + ex); + } + } + } +} diff --git a/models-base/src/main/java/org/onap/policy/models/base/PfConceptKey.java b/models-base/src/main/java/org/onap/policy/models/base/PfConceptKey.java index efcbe392c..695ca4712 100644 --- a/models-base/src/main/java/org/onap/policy/models/base/PfConceptKey.java +++ b/models-base/src/main/java/org/onap/policy/models/base/PfConceptKey.java @@ -28,6 +28,7 @@ import javax.persistence.Embeddable; import lombok.Data; import lombok.EqualsAndHashCode; +import lombok.NonNull; import org.onap.policy.common.utils.validation.Assertions; import org.onap.policy.models.base.PfValidationResult.ValidationResult; @@ -67,7 +68,7 @@ public class PfConceptKey extends PfKey { * * @param copyConcept the concept to copy from */ - public PfConceptKey(final PfConceptKey copyConcept) { + public PfConceptKey(@NonNull final PfConceptKey copyConcept) { super(copyConcept); } @@ -77,7 +78,7 @@ public class PfConceptKey extends PfKey { * @param name the key name * @param version the key version */ - public PfConceptKey(final String name, final String version) { + public PfConceptKey(@NonNull final String name, @NonNull final String version) { super(); this.name = Assertions.validateStringParameter(NAME_TOKEN, name, NAME_REGEXP); this.version = Assertions.validateStringParameter(VERSION_TOKEN, version, VERSION_REGEXP); @@ -88,9 +89,7 @@ public class PfConceptKey extends PfKey { * * @param id the key ID in a format that respects the KEY_ID_REGEXP */ - public PfConceptKey(final String id) { - Assertions.argumentNotNull(id, "id may not be null"); - + public PfConceptKey(@NonNull final String id) { // Check the incoming ID is valid Assertions.validateStringParameter("id", id, KEY_ID_REGEXP); @@ -131,7 +130,12 @@ public class PfConceptKey extends PfKey { } @Override - public PfKey.Compatibility getCompatibility(final PfKey otherKey) { + public boolean isNullKey() { + return this.equals(PfConceptKey.getNullKey()); + } + + @Override + public PfKey.Compatibility getCompatibility(@NonNull final PfKey otherKey) { if (!(otherKey instanceof PfConceptKey)) { return Compatibility.DIFFERENT; } @@ -161,7 +165,7 @@ public class PfConceptKey extends PfKey { } @Override - public boolean isCompatible(final PfKey otherKey) { + public boolean isCompatible(@NonNull final PfKey otherKey) { if (!(otherKey instanceof PfConceptKey)) { return false; } @@ -212,7 +216,7 @@ public class PfConceptKey extends PfKey { } @Override - public int compareTo(final PfConcept otherObj) { + public int compareTo(@NonNull final PfConcept otherObj) { Assertions.argumentNotNull(otherObj, "comparison object may not be null"); if (this == otherObj) { diff --git a/models-base/src/main/java/org/onap/policy/models/base/PfKey.java b/models-base/src/main/java/org/onap/policy/models/base/PfKey.java index dda4cdc03..6e9035e95 100644 --- a/models-base/src/main/java/org/onap/policy/models/base/PfKey.java +++ b/models-base/src/main/java/org/onap/policy/models/base/PfKey.java @@ -20,6 +20,8 @@ package org.onap.policy.models.base; +import lombok.NonNull; + /** * The key uniquely identifies every entity in the system. This class is an abstract class to give a common parent for * all key types in the system. @@ -89,7 +91,7 @@ public abstract class PfKey extends PfConcept { * @param otherKey the key to check compatibility against * @return the compatibility result of the check */ - public abstract Compatibility getCompatibility(PfKey otherKey); + public abstract Compatibility getCompatibility(@NonNull PfKey otherKey); /** * Check if two keys are compatible, that is the keys are IDENTICAL or have only MINOR, PATCH differences. @@ -97,5 +99,12 @@ public abstract class PfKey extends PfConcept { * @param otherKey the key to check compatibility against * @return true, if the keys are compatible */ - public abstract boolean isCompatible(PfKey otherKey); + public abstract boolean isCompatible(@NonNull PfKey otherKey); + + /** + * Check if a key equals its null key. + * + * @return true, if the key is a null key + */ + public abstract boolean isNullKey(); } diff --git a/models-base/src/main/java/org/onap/policy/models/base/PfKeyUse.java b/models-base/src/main/java/org/onap/policy/models/base/PfKeyUse.java index 0eb55a711..57141c2fa 100644 --- a/models-base/src/main/java/org/onap/policy/models/base/PfKeyUse.java +++ b/models-base/src/main/java/org/onap/policy/models/base/PfKeyUse.java @@ -22,16 +22,20 @@ package org.onap.policy.models.base; import java.util.List; +import javax.ws.rs.core.Response; + import lombok.EqualsAndHashCode; +import lombok.NonNull; import lombok.ToString; import org.onap.policy.common.utils.validation.Assertions; import org.onap.policy.models.base.PfValidationResult.ValidationResult; /** - * This class records a usage of a key in the system. When the list of keys being used by a concept is built using the - * getKeys() method of the {@link PfConcept} class, an instance of this class is created for every key occurrence. The - * list of keys returned by the getKeys() method is a list of {@link PfKeyUse} objects. + * This class records a usage of a key in the system. When the list of keys being used by a concept + * is built using the getKeys() method of the {@link PfConcept} class, an instance of this class is + * created for every key occurrence. The list of keys returned by the getKeys() method is a list of + * {@link PfKeyUse} objects. * *

Validation checks that each key is valid. */ @@ -50,22 +54,21 @@ public class PfKeyUse extends PfKey { } /** - * Copy constructor. + * This constructor creates an instance of this class, and holds a reference to a used key. * - * @param copyConcept the concept to copy from + * @param usedKey a used key */ - public PfKeyUse(final PfKeyUse copyConcept) { - super(copyConcept); + public PfKeyUse(@NonNull final PfKey usedKey) { + this.usedKey = usedKey; } /** - * This constructor creates an instance of this class, and holds a reference to a used key. + * Copy constructor. * - * @param usedKey a used key + * @param copyConcept the concept to copy from */ - public PfKeyUse(final PfKey usedKey) { - Assertions.argumentNotNull(usedKey, "usedKey may not be null"); - this.usedKey = usedKey; + public PfKeyUse(@NonNull final PfKeyUse copyConcept) { + super(copyConcept); } @Override @@ -83,56 +86,42 @@ public class PfKeyUse extends PfKey { return usedKey.getId(); } + @Override + public boolean isNullKey() { + return usedKey.isNullKey(); + } + /** * Sets the key. * * @param key the key */ - public void setKey(final PfKey key) { - Assertions.argumentNotNull(key, "usedKey may not be null"); + public void setKey(@NonNull final PfKey key) { this.usedKey = key; } @Override - public PfKey.Compatibility getCompatibility(final PfKey otherKey) { + public PfKey.Compatibility getCompatibility(@NonNull final PfKey otherKey) { return usedKey.getCompatibility(otherKey); } @Override - public boolean isCompatible(final PfKey otherKey) { + public boolean isCompatible(@NonNull final PfKey otherKey) { return usedKey.isCompatible(otherKey); } - @Override - public PfValidationResult validate(final PfValidationResult result) { - if (usedKey.equals(PfConceptKey.getNullKey())) { - result.addValidationMessage(new PfValidationMessage(usedKey, this.getClass(), ValidationResult.INVALID, - "usedKey is a null key")); - } - return usedKey.validate(result); - } - @Override public void clean() { usedKey.clean(); } @Override - public PfConcept copyTo(final PfConcept target) { - Assertions.argumentNotNull(target, "target may not be null"); - - final Object copyObject = target; - Assertions.instanceOf(copyObject, PfKeyUse.class); - - final PfKeyUse copy = ((PfKeyUse) copyObject); - try { - copy.usedKey = usedKey.getClass().newInstance(); - } catch (final Exception e) { - throw new PfModelRuntimeException("error copying concept key: " + e.getMessage(), e); + public PfValidationResult validate(@NonNull final PfValidationResult result) { + if (usedKey.isNullKey()) { + result.addValidationMessage(new PfValidationMessage(usedKey, this.getClass(), ValidationResult.INVALID, + "usedKey is a null key")); } - usedKey.copyTo(copy.usedKey); - - return copy; + return usedKey.validate(result); } @Override @@ -150,4 +139,21 @@ public class PfKeyUse extends PfKey { return usedKey.compareTo(other.usedKey); } + + @Override + public PfConcept copyTo(@NonNull final PfConcept target) { + final Object copyObject = target; + Assertions.instanceOf(copyObject, PfKeyUse.class); + + final PfKeyUse copy = ((PfKeyUse) copyObject); + try { + copy.usedKey = usedKey.getClass().newInstance(); + } catch (final Exception e) { + throw new PfModelRuntimeException(Response.Status.INTERNAL_SERVER_ERROR, + "error copying concept key: " + e.getMessage(), e); + } + usedKey.copyTo(copy.usedKey); + + return copy; + } } diff --git a/models-base/src/main/java/org/onap/policy/models/base/PfModel.java b/models-base/src/main/java/org/onap/policy/models/base/PfModel.java index c9174bde8..3dc233b02 100644 --- a/models-base/src/main/java/org/onap/policy/models/base/PfModel.java +++ b/models-base/src/main/java/org/onap/policy/models/base/PfModel.java @@ -63,8 +63,7 @@ public abstract class PfModel extends PfConcept { private static final long serialVersionUID = -771659065637205430L; @EmbeddedId - @NonNull - private PfConceptKey key = PfConceptKey.getNullKey(); + private PfConceptKey key; /** * The Default Constructor creates this concept with a NULL artifact key. @@ -73,27 +72,27 @@ public abstract class PfModel extends PfConcept { this(new PfConceptKey()); } - /** - * Copy constructor. - * - * @param copyConcept the concept to copy from - */ - public PfModel(final PfModel copyConcept) { - super(copyConcept); - } - /** * Constructor to create this concept with the specified key. * * @param key the key of this concept */ - public PfModel(final PfConceptKey key) { + public PfModel(@NonNull final PfConceptKey key) { super(); Assertions.argumentNotNull(key, "key may not be null"); this.key = key; } + /** + * Copy constructor. + * + * @param copyConcept the concept to copy from + */ + public PfModel(@NonNull final PfModel copyConcept) { + super(copyConcept); + } + /** * Registers this model with the {@link PfModelService}. All models are registered with the * model service so that models can be references from anywhere in the Policy Framework system @@ -107,10 +106,15 @@ public abstract class PfModel extends PfConcept { } @Override - public PfValidationResult validate(final PfValidationResult resultIn) { + public void clean() { + key.clean(); + } + + @Override + public PfValidationResult validate(@NonNull final PfValidationResult resultIn) { PfValidationResult result = resultIn; - if (key.equals(PfConceptKey.getNullKey())) { + if (key.isNullKey()) { result.addValidationMessage( new PfValidationMessage(key, this.getClass(), ValidationResult.INVALID, "key is a null key")); } @@ -129,7 +133,7 @@ public abstract class PfModel extends PfConcept { } else if (pfKey instanceof PfReferenceKey) { result = validateReferenceKeyInModel((PfReferenceKey) pfKey, referenceKeySet, result); } - // It must be an PfKeyUse, nothing else is legal + // It must be a PfKeyUse, nothing else is legal else { usedKeySet.add((PfKeyUse) pfKey); } @@ -160,7 +164,7 @@ public abstract class PfModel extends PfConcept { private PfValidationResult validateArtifactKeyInModel(final PfConceptKey artifactKey, final Set artifactKeySet, final PfValidationResult result) { // Null key check - if (artifactKey.equals(PfConceptKey.getNullKey())) { + if (artifactKey.isNullKey()) { result.addValidationMessage(new PfValidationMessage(key, this.getClass(), ValidationResult.INVALID, "key " + artifactKey + IS_A_NULL_KEY)); } @@ -194,13 +198,13 @@ public abstract class PfModel extends PfConcept { private PfValidationResult validateReferenceKeyInModel(final PfReferenceKey referenceKey, final Set referenceKeySet, final PfValidationResult result) { // Null key check - if (referenceKey.equals(PfReferenceKey.getNullKey())) { + if (referenceKey.isNullKey()) { result.addValidationMessage(new PfValidationMessage(key, this.getClass(), ValidationResult.INVALID, "key " + referenceKey + IS_A_NULL_KEY)); } // Null parent key check - if (referenceKey.getParentConceptKey().equals(PfConceptKey.getNullKey())) { + if (referenceKey.getParentConceptKey().isNullKey()) { result.addValidationMessage(new PfValidationMessage(key, this.getClass(), ValidationResult.INVALID, "parent artifact key of key " + referenceKey + IS_A_NULL_KEY)); } @@ -261,29 +265,6 @@ public abstract class PfModel extends PfConcept { return result; } - @Override - public void clean() { - key.clean(); - } - - @Override - public PfConcept copyTo(final PfConcept target) { - Assertions.argumentNotNull(target, "target may not be null"); - - final Object copyObject = target; - Assertions.instanceOf(copyObject, PfModel.class); - - final PfModel copy = ((PfModel) copyObject); - copy.setKey(new PfConceptKey(key)); - - return copy; - } - - /* - * (non-Javadoc) - * - * @see java.lang.Comparable#compareTo(java.lang.Object) - */ @Override public int compareTo(final PfConcept otherObj) { if (otherObj == null) { @@ -300,4 +281,14 @@ public abstract class PfModel extends PfConcept { return key.compareTo(other.key); } + + @Override + public PfConcept copyTo(@NonNull final PfConcept target) { + Assertions.instanceOf(target, PfModel.class); + + final PfModel copy = ((PfModel) target); + copy.setKey(new PfConceptKey(key)); + + return copy; + } } diff --git a/models-base/src/main/java/org/onap/policy/models/base/PfModelException.java b/models-base/src/main/java/org/onap/policy/models/base/PfModelException.java index 3d1bb1794..97ea7de00 100644 --- a/models-base/src/main/java/org/onap/policy/models/base/PfModelException.java +++ b/models-base/src/main/java/org/onap/policy/models/base/PfModelException.java @@ -20,54 +20,71 @@ package org.onap.policy.models.base; +import javax.ws.rs.core.Response; + +import lombok.Getter; +import lombok.ToString; + /** * This class is a base exception from which all model exceptions are sub classes. */ +@Getter +@ToString public class PfModelException extends Exception { private static final long serialVersionUID = -8507246953751956974L; + // The status code on the exception + private final Response.Status statusCode; + // The object on which the exception was thrown private final transient Object object; /** * Instantiates a new model exception. * + * @param statusCode the return code for the exception * @param message the message on the exception */ - public PfModelException(final String message) { - this(message, null); + public PfModelException(final Response.Status statusCode, final String message) { + this(statusCode, message, null); } /** * Instantiates a new model exception. * + * @param statusCode the return code for the exception * @param message the message on the exception * @param object the object that the exception was thrown on */ - public PfModelException(final String message, final Object object) { + public PfModelException(final Response.Status statusCode, final String message, final Object object) { super(message); + this.statusCode = statusCode; this.object = object; } /** * Instantiates a new model exception. * + * @param statusCode the return code for the exception * @param message the message on the exception * @param exception the exception that caused this exception */ - public PfModelException(final String message, final Exception exception) { - this(message, exception, null); + public PfModelException(final Response.Status statusCode, final String message, final Exception exception) { + this(statusCode, message, exception, null); } /** * Instantiates a new exception. * + * @param statusCode the return code for the exception * @param message the message on the exception * @param exception the exception that caused this exception * @param object the object that the exception was thrown on */ - public PfModelException(final String message, final Exception exception, final Object object) { + public PfModelException(final Response.Status statusCode, final String message, final Exception exception, + final Object object) { super(message, exception); + this.statusCode = statusCode; this.object = object; } @@ -97,13 +114,4 @@ public class PfModelException extends Exception { return builder.toString(); } - - /** - * Get the object on which the exception was thrown. - * - * @return The object on which the exception was thrown - */ - public Object getObject() { - return object; - } } diff --git a/models-base/src/main/java/org/onap/policy/models/base/PfModelRuntimeException.java b/models-base/src/main/java/org/onap/policy/models/base/PfModelRuntimeException.java index 0780a9e20..c4684bc09 100644 --- a/models-base/src/main/java/org/onap/policy/models/base/PfModelRuntimeException.java +++ b/models-base/src/main/java/org/onap/policy/models/base/PfModelRuntimeException.java @@ -20,56 +20,73 @@ package org.onap.policy.models.base; +import javax.ws.rs.core.Response; + +import lombok.Getter; +import lombok.ToString; + /** * This class is a base model run time exception from which all model run time exceptions are sub * classes. */ +@Getter +@ToString public class PfModelRuntimeException extends RuntimeException { private static final long serialVersionUID = -8507246953751956974L; + // The return code on the exception + private final Response.Status statusCode; + // The object on which the exception was thrown private final transient Object object; /** * Instantiates a new model runtime exception. * + * @param statusCode the return code for the exception * @param message the message on the exception */ - public PfModelRuntimeException(final String message) { - this(message, null); + public PfModelRuntimeException(final Response.Status statusCode, final String message) { + this(statusCode, message, null); } /** * Instantiates a new model runtime exception. * + * @param statusCode the return code for the exception * @param message the message on the exception * @param object the object that the exception was thrown on */ - public PfModelRuntimeException(final String message, final Object object) { + public PfModelRuntimeException(final Response.Status statusCode, final String message, final Object object) { super(message); this.object = object; + this.statusCode = statusCode; } /** * Instantiates a new model runtime exception. * + * @param statusCode the return code for the exception * @param message the message on the exception * @param exception the exception that caused this model exception */ - public PfModelRuntimeException(final String message, final Exception exception) { - this(message, exception, null); + public PfModelRuntimeException(final Response.Status statusCode, final String message, final Exception exception) { + this(statusCode, message, exception, null); } /** * Instantiates a new model runtime exception. * + * @param statusCode the return code for the exception * @param message the message on the exception * @param exception the exception that caused this model exception * @param object the object that the exception was thrown on */ - public PfModelRuntimeException(final String message, final Exception exception, final Object object) { + public PfModelRuntimeException(final Response.Status statusCode, final String message, final Exception exception, + final Object object) { super(message, exception); this.object = object; + this.statusCode = statusCode; } /** @@ -80,13 +97,4 @@ public class PfModelRuntimeException extends RuntimeException { public String getCascadedMessage() { return PfModelException.buildCascadedMessage(this); } - - /** - * Get the object on which the exception was thrown. - * - * @return The object - */ - public Object getObject() { - return object; - } } diff --git a/models-base/src/main/java/org/onap/policy/models/base/PfModelService.java b/models-base/src/main/java/org/onap/policy/models/base/PfModelService.java index c02de6aa7..67ba59c8b 100644 --- a/models-base/src/main/java/org/onap/policy/models/base/PfModelService.java +++ b/models-base/src/main/java/org/onap/policy/models/base/PfModelService.java @@ -23,6 +23,10 @@ package org.onap.policy.models.base; import java.util.Map; import java.util.concurrent.ConcurrentHashMap; +import javax.ws.rs.core.Response; + +import lombok.NonNull; + /** * The model service makes Policy Framework models available to all classes in a JVM. * @@ -37,7 +41,7 @@ import java.util.concurrent.ConcurrentHashMap; */ public abstract class PfModelService { // The map holding the models - private static Map, PfConcept> modelMap = new ConcurrentHashMap<>(); + private static Map modelMap = new ConcurrentHashMap<>(); /** * This class is an abstract static class that cannot be extended. @@ -48,37 +52,36 @@ public abstract class PfModelService { * Register a model with the model service. * * @param the generic type - * @param modelClass the class of the model, used to index the model + * @param modelKey the key of the model, used to index the model * @param model The model */ - public static void registerModel(final Class modelClass, final M model) { - modelMap.put(modelClass, model); + public static void registerModel(@NonNull final String modelKey, @NonNull final M model) { + modelMap.put(modelKey, model); } /** * Remove a model from the model service. * - * @param the generic type - * @param modelClass the class of the model, used to index the model + * @param modelKey the key of the model, used to index the model */ - public static void deregisterModel(final Class modelClass) { - modelMap.remove(modelClass); + public static void deregisterModel(@NonNull final String modelKey) { + modelMap.remove(modelKey); } /** * Get a model from the model service. * * @param the generic type - * @param modelClass the class of the model, used to index the model + * @param modelKey the key of the model, used to index the model * @return The model */ @SuppressWarnings("unchecked") - public static M getModel(final Class modelClass) { - final M model = (M) modelMap.get(modelClass); + public static M getModel(@NonNull final String modelKey) { + final M model = (M) modelMap.get(modelKey); if (model == null) { - throw new PfModelRuntimeException( - "Model for " + modelClass.getCanonicalName() + " not found in model service"); + throw new PfModelRuntimeException(Response.Status.INTERNAL_SERVER_ERROR, + "Model for name " + modelKey + " not found in model service"); } return model; @@ -87,12 +90,11 @@ public abstract class PfModelService { /** * Check if a model is defined on the model service. * - * @param the generic type - * @param modelClass the class of the model, used to index the model + * @param modelKey the key of the model, used to index the model * @return true if the model is defined */ - public static boolean existsModel(final Class modelClass) { - return modelMap.get(modelClass) != null; + public static boolean existsModel(final String modelKey) { + return modelMap.get(modelKey) != null; } /** diff --git a/models-base/src/main/java/org/onap/policy/models/base/PfReferenceKey.java b/models-base/src/main/java/org/onap/policy/models/base/PfReferenceKey.java index e3b92c0e9..2e9f48ba5 100644 --- a/models-base/src/main/java/org/onap/policy/models/base/PfReferenceKey.java +++ b/models-base/src/main/java/org/onap/policy/models/base/PfReferenceKey.java @@ -243,6 +243,11 @@ public class PfReferenceKey extends PfKey { return parentKeyName + ':' + parentKeyVersion + ':' + parentLocalName + ':' + localName; } + @Override + public boolean isNullKey() { + return this.equals(PfReferenceKey.getNullKey()); + } + /** * Gets the parent concept key of this reference key. * diff --git a/models-base/src/main/java/org/onap/policy/models/base/PfUtils.java b/models-base/src/main/java/org/onap/policy/models/base/PfUtils.java new file mode 100644 index 000000000..a18315ceb --- /dev/null +++ b/models-base/src/main/java/org/onap/policy/models/base/PfUtils.java @@ -0,0 +1,59 @@ +/*- + * ============LICENSE_START======================================================= + * Copyright (C) 2019 Nordix Foundation. + * ================================================================================ + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * SPDX-License-Identifier: Apache-2.0 + * ============LICENSE_END========================================================= + */ + +package org.onap.policy.models.base; + +/** + * Utility class for Policy Framework concept utilities. + * + * @author Liam Fallon (liam.fallon@est.tech) + */ +public final class PfUtils { + private PfUtils() { + // Cannot be subclassed + } + + /** + * Compare two objects using their equals methods, nulls are allowed. + * + * @param leftObject the first object + * @param rightObject the second object + * @return a measure of the comparison + */ + public static int compareObjects(final Object leftObject, final Object rightObject) { + if (leftObject == null && rightObject == null) { + return 0; + } + + if (leftObject == null) { + return 1; + } + + if (rightObject == null) { + return -1; + } + + if (!leftObject.equals(rightObject)) { + return leftObject.hashCode() - rightObject.hashCode(); + } + + return 0; + } +} diff --git a/models-base/src/main/java/org/onap/policy/models/base/PfValidationResult.java b/models-base/src/main/java/org/onap/policy/models/base/PfValidationResult.java index 284c11ac2..4f8d06bdc 100644 --- a/models-base/src/main/java/org/onap/policy/models/base/PfValidationResult.java +++ b/models-base/src/main/java/org/onap/policy/models/base/PfValidationResult.java @@ -23,9 +23,12 @@ package org.onap.policy.models.base; import java.util.LinkedList; import java.util.List; +import lombok.Getter; + /** - * This class records the result of a validation and holds all validatino observation messages. + * This class records the result of a validation and holds all validation observation messages. */ +@Getter public class PfValidationResult { /** * The ValidationResult enumeration describes the severity of a validation result. @@ -76,24 +79,6 @@ public class PfValidationResult { return validationResult == ValidationResult.VALID || validationResult == ValidationResult.OBSERVATION; } - /** - * Gets the validation result. - * - * @return the validation result on a concept - */ - public ValidationResult getValidationResult() { - return validationResult; - } - - /** - * Gets the list of validation results on the concept. - * - * @return the list of validaiton results - */ - public List getMessageList() { - return messageList; - } - /** * Adds a validation message to the validation result, used by validate() implementations on * {@link PfConcept} subclasses to report validaiton observations. -- cgit 1.2.3-korg