From 70b5fce78f12863c6abc0ff31cfe0cb18c196584 Mon Sep 17 00:00:00 2001 From: "aravind.est" Date: Thu, 26 Oct 2023 16:26:48 +0100 Subject: [PATCH 1/1] Add validator to check atleast one non null field check Validator added to check atleast one non null field exists in the provided class. Issue-ID: NONRTRIC-952 Signed-off-by: aravind.est Change-Id: Ic525109aaaaa9f165b4562d10b4967987073a9f2 --- .../AutomationCompositionElementHandler.java | 4 +- .../dme/models/ConfigurationEntity.java | 8 ++- .../dme/validator/AtleastOneNonNullField.java | 43 ++++++++++++ .../validator/AtleastOneNonNullFieldValidator.java | 58 ++++++++++++++++ .../AtleastOneNonNullFieldValidatorTest.java | 79 ++++++++++++++++++++++ 5 files changed, 186 insertions(+), 6 deletions(-) create mode 100755 participants/participant-impl-dme/src/main/java/org/oransc/participant/dme/validator/AtleastOneNonNullField.java create mode 100755 participants/participant-impl-dme/src/main/java/org/oransc/participant/dme/validator/AtleastOneNonNullFieldValidator.java create mode 100755 participants/participant-impl-dme/src/test/java/org/oransc/participant/dme/validator/AtleastOneNonNullFieldValidatorTest.java diff --git a/participants/participant-impl-dme/src/main/java/org/oransc/participant/dme/handler/AutomationCompositionElementHandler.java b/participants/participant-impl-dme/src/main/java/org/oransc/participant/dme/handler/AutomationCompositionElementHandler.java index 612295e..71d9aaf 100755 --- a/participants/participant-impl-dme/src/main/java/org/oransc/participant/dme/handler/AutomationCompositionElementHandler.java +++ b/participants/participant-impl-dme/src/main/java/org/oransc/participant/dme/handler/AutomationCompositionElementHandler.java @@ -103,9 +103,7 @@ public class AutomationCompositionElementHandler implements AutomationCompositio var configurationEntity = CODER.convert(properties, ConfigurationEntity.class); var violations = Validation.buildDefaultValidatorFactory().getValidator().validate(configurationEntity); if (violations.isEmpty()) { - if ((configurationEntity.getInfoTypeEntities() != null - || configurationEntity.getDataProducerEntities() != null - || configurationEntity.getDataConsumerEntities() != null) && acDmeClient.isDmeHealthy()) { + if (acDmeClient.isDmeHealthy()) { if (configurationEntity.getInfoTypeEntities() != null) { acDmeClient.createInfoType(configurationEntity.getInfoTypeEntities().stream().collect( Collectors.toMap(InfoTypeEntity::getInfoTypeId, InfoTypeEntity::getPayload))); diff --git a/participants/participant-impl-dme/src/main/java/org/oransc/participant/dme/models/ConfigurationEntity.java b/participants/participant-impl-dme/src/main/java/org/oransc/participant/dme/models/ConfigurationEntity.java index a312226..058ab02 100755 --- a/participants/participant-impl-dme/src/main/java/org/oransc/participant/dme/models/ConfigurationEntity.java +++ b/participants/participant-impl-dme/src/main/java/org/oransc/participant/dme/models/ConfigurationEntity.java @@ -24,17 +24,19 @@ import jakarta.validation.Valid; import java.util.List; import lombok.AllArgsConstructor; import lombok.Data; +import org.oransc.participant.dme.validator.AtleastOneNonNullField; @Data @AllArgsConstructor +@AtleastOneNonNullField(fieldNames = {"infoTypeEntities", "dataProducerEntities", "dataConsumerEntities"}) public class ConfigurationEntity { @Valid - private List infoTypeEntities; + List infoTypeEntities; @Valid - private List dataProducerEntities; + List dataProducerEntities; @Valid - private List dataConsumerEntities; + List dataConsumerEntities; } diff --git a/participants/participant-impl-dme/src/main/java/org/oransc/participant/dme/validator/AtleastOneNonNullField.java b/participants/participant-impl-dme/src/main/java/org/oransc/participant/dme/validator/AtleastOneNonNullField.java new file mode 100755 index 0000000..b79feb7 --- /dev/null +++ b/participants/participant-impl-dme/src/main/java/org/oransc/participant/dme/validator/AtleastOneNonNullField.java @@ -0,0 +1,43 @@ +/*- + * ============LICENSE_START======================================================= + * Copyright (C) 2023 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.oransc.participant.dme.validator; + +import jakarta.validation.Constraint; +import java.lang.annotation.Documented; +import java.lang.annotation.ElementType; +import java.lang.annotation.Retention; +import java.lang.annotation.RetentionPolicy; +import java.lang.annotation.Target; + +@Target(ElementType.TYPE) +@Retention(RetentionPolicy.RUNTIME) +@Documented +@Constraint(validatedBy = AtleastOneNonNullFieldValidator.class) +public @interface AtleastOneNonNullField { + + String message() default "Atleast one field should not be null."; + + Class[] groups() default {}; + + Class[] payload() default {}; + + String[] fieldNames(); +} diff --git a/participants/participant-impl-dme/src/main/java/org/oransc/participant/dme/validator/AtleastOneNonNullFieldValidator.java b/participants/participant-impl-dme/src/main/java/org/oransc/participant/dme/validator/AtleastOneNonNullFieldValidator.java new file mode 100755 index 0000000..6e66a25 --- /dev/null +++ b/participants/participant-impl-dme/src/main/java/org/oransc/participant/dme/validator/AtleastOneNonNullFieldValidator.java @@ -0,0 +1,58 @@ +/*- + * ============LICENSE_START======================================================= + * Copyright (C) 2023 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.oransc.participant.dme.validator; + +import jakarta.validation.ConstraintValidator; +import jakarta.validation.ConstraintValidatorContext; +import java.beans.PropertyDescriptor; +import java.lang.reflect.InvocationTargetException; +import org.springframework.beans.BeanUtils; + +public class AtleastOneNonNullFieldValidator implements ConstraintValidator { + + String[] fieldNames; + + @Override + public void initialize(AtleastOneNonNullField atleastOneNonNullField) { + fieldNames = atleastOneNonNullField.fieldNames(); + } + + @Override + public boolean isValid(Object object, ConstraintValidatorContext constraintValidatorContext) { + if (object == null) { + return false; + } + for (String fieldName : fieldNames) { + try { + PropertyDescriptor propertyDescriptor = BeanUtils.getPropertyDescriptor(object.getClass(), fieldName); + if (propertyDescriptor != null) { + Object fieldValue = propertyDescriptor.getReadMethod().invoke(object); + if (fieldValue != null) { + return true; + } + } + } catch (IllegalAccessException | InvocationTargetException e) { + return false; + } + } + return false; + } +} diff --git a/participants/participant-impl-dme/src/test/java/org/oransc/participant/dme/validator/AtleastOneNonNullFieldValidatorTest.java b/participants/participant-impl-dme/src/test/java/org/oransc/participant/dme/validator/AtleastOneNonNullFieldValidatorTest.java new file mode 100755 index 0000000..bbd3d6f --- /dev/null +++ b/participants/participant-impl-dme/src/test/java/org/oransc/participant/dme/validator/AtleastOneNonNullFieldValidatorTest.java @@ -0,0 +1,79 @@ +/*- + * ============LICENSE_START======================================================= + * Copyright (C) 2023 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.oransc.participant.dme.validator; + +import static org.junit.jupiter.api.Assertions.assertFalse; +import static org.junit.jupiter.api.Assertions.assertTrue; +import static org.mockito.Mockito.when; + +import jakarta.validation.ConstraintValidatorContext; +import java.util.List; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.api.extension.ExtendWith; +import org.mockito.Mock; +import org.oransc.participant.dme.models.ConfigurationEntity; +import org.springframework.test.context.junit.jupiter.SpringExtension; + +@ExtendWith(SpringExtension.class) +class AtleastOneNonNullFieldValidatorTest { + + @Mock + AtleastOneNonNullField atleastOneNonNullField; + @Mock + ConstraintValidatorContext constraintValidatorContext; + + String[] fields = new String[] {"infoTypeEntities", "dataProducerEntities", "dataConsumerEntities"}; + + @Test + void testValidObject() { + when(atleastOneNonNullField.fieldNames()).thenReturn(fields); + AtleastOneNonNullFieldValidator atleastOneNonNullFieldValidator = new AtleastOneNonNullFieldValidator(); + atleastOneNonNullFieldValidator.initialize(atleastOneNonNullField); + ConfigurationEntity configurationEntity = new ConfigurationEntity(List.of(), List.of(), List.of()); + assertTrue(atleastOneNonNullFieldValidator.isValid(configurationEntity, constraintValidatorContext)); + } + + @Test + void testInvalidObject() { + when(atleastOneNonNullField.fieldNames()).thenReturn(fields); + AtleastOneNonNullFieldValidator atleastOneNonNullFieldValidator = new AtleastOneNonNullFieldValidator(); + atleastOneNonNullFieldValidator.initialize(atleastOneNonNullField); + ConfigurationEntity configurationEntity = new ConfigurationEntity(null, null, null); + assertFalse(atleastOneNonNullFieldValidator.isValid(configurationEntity, constraintValidatorContext)); + } + + @Test + void testInvalidField() { + when(atleastOneNonNullField.fieldNames()).thenReturn(new String[] {"invalidField"}); + AtleastOneNonNullFieldValidator atleastOneNonNullFieldValidator = new AtleastOneNonNullFieldValidator(); + atleastOneNonNullFieldValidator.initialize(atleastOneNonNullField); + ConfigurationEntity configurationEntity = new ConfigurationEntity(List.of(), List.of(), List.of()); + assertFalse(atleastOneNonNullFieldValidator.isValid(configurationEntity, constraintValidatorContext)); + } + + @Test + void testNullObject() { + when(atleastOneNonNullField.fieldNames()).thenReturn(new String[] {"invalidField"}); + AtleastOneNonNullFieldValidator atleastOneNonNullFieldValidator = new AtleastOneNonNullFieldValidator(); + atleastOneNonNullFieldValidator.initialize(atleastOneNonNullField); + assertFalse(atleastOneNonNullFieldValidator.isValid(null, constraintValidatorContext)); + } +} -- 2.16.6