aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--cps-ncmp-service/src/main/java/org/onap/cps/ncmp/api/inventory/models/NcmpServiceCmHandle.java9
-rw-r--r--cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/datajobs/WriteRequestExaminer.java8
-rw-r--r--cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/dmi/DmiServiceNameResolver.java92
-rw-r--r--cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/inventory/AlternateIdChecker.java5
-rw-r--r--cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/inventory/InventoryPersistence.java16
-rw-r--r--cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/inventory/InventoryPersistenceImpl.java13
-rw-r--r--cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/inventory/models/YangModelCmHandle.java14
-rw-r--r--cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/inventory/trustlevel/TrustLevelManager.java18
-rw-r--r--cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/utils/AlternateIdMatcher.java19
-rw-r--r--cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/utils/YangDataConverter.java6
-rw-r--r--cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/datajobs/WriteRequestExaminerSpec.groovy36
-rw-r--r--cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/inventory/AlternateIdCheckerSpec.groovy11
-rw-r--r--cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/inventory/InventoryPersistenceImplSpec.groovy25
-rw-r--r--cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/inventory/trustlevel/TrustLevelManagerSpec.groovy14
-rw-r--r--cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/utils/AlternateIdMatcherSpec.groovy16
-rw-r--r--cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/utils/YangDataConverterSpec.groovy8
-rw-r--r--cps-service/src/main/java/org/onap/cps/api/CpsQueryService.java15
-rw-r--r--cps-service/src/main/java/org/onap/cps/api/impl/CpsQueryServiceImpl.java19
-rw-r--r--cps-service/src/test/groovy/org/onap/cps/api/impl/CpsQueryServiceImplSpec.groovy8
-rw-r--r--integration-test/src/test/groovy/org/onap/cps/integration/functional/cps/QueryServiceIntegrationSpec.groovy39
-rw-r--r--integration-test/src/test/groovy/org/onap/cps/integration/performance/ncmp/CmHandleQueryByAlternateIdPerfTest.groovy2
21 files changed, 291 insertions, 102 deletions
diff --git a/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/api/inventory/models/NcmpServiceCmHandle.java b/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/api/inventory/models/NcmpServiceCmHandle.java
index 3ebceed9d7..25c9f76660 100644
--- a/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/api/inventory/models/NcmpServiceCmHandle.java
+++ b/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/api/inventory/models/NcmpServiceCmHandle.java
@@ -42,6 +42,15 @@ public class NcmpServiceCmHandle {
private String cmHandleId;
@JsonSetter(nulls = Nulls.AS_EMPTY)
+ private String dmiServiceName;
+
+ @JsonSetter(nulls = Nulls.AS_EMPTY)
+ private String dmiDataServiceName;
+
+ @JsonSetter(nulls = Nulls.AS_EMPTY)
+ private String dmiModelServiceName;
+
+ @JsonSetter(nulls = Nulls.AS_EMPTY)
private Map<String, String> dmiProperties = Collections.emptyMap();
@JsonSetter(nulls = Nulls.AS_EMPTY)
diff --git a/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/datajobs/WriteRequestExaminer.java b/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/datajobs/WriteRequestExaminer.java
index e13d3c2328..429a3790d4 100644
--- a/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/datajobs/WriteRequestExaminer.java
+++ b/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/datajobs/WriteRequestExaminer.java
@@ -34,8 +34,6 @@ import org.onap.cps.ncmp.api.datajobs.models.WriteOperation;
import org.onap.cps.ncmp.impl.inventory.models.YangModelCmHandle;
import org.onap.cps.ncmp.impl.models.RequiredDmiService;
import org.onap.cps.ncmp.impl.utils.AlternateIdMatcher;
-import org.onap.cps.ncmp.impl.utils.YangDataConverter;
-import org.onap.cps.spi.model.DataNode;
import org.springframework.stereotype.Service;
@Slf4j
@@ -67,10 +65,8 @@ public class WriteRequestExaminer {
final Map<ProducerKey, List<DmiWriteOperation>> dmiWriteOperationsPerProducerKey,
final WriteOperation writeOperation) {
log.debug("data job id for write operation is: {}", dataJobId);
- final DataNode dataNode = alternateIdMatcher
- .getCmHandleDataNodeByLongestMatchingAlternateId(writeOperation.path(), PATH_SEPARATOR);
-
- final YangModelCmHandle yangModelCmHandle = YangDataConverter.toYangModelCmHandle(dataNode);
+ final YangModelCmHandle yangModelCmHandle = alternateIdMatcher
+ .getYangModelCmHandleByLongestMatchingAlternateId(writeOperation.path(), PATH_SEPARATOR);
final DmiWriteOperation dmiWriteOperation = createDmiWriteOperation(writeOperation, yangModelCmHandle);
diff --git a/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/dmi/DmiServiceNameResolver.java b/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/dmi/DmiServiceNameResolver.java
new file mode 100644
index 0000000000..e9378daaec
--- /dev/null
+++ b/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/dmi/DmiServiceNameResolver.java
@@ -0,0 +1,92 @@
+/*
+ * ============LICENSE_START=======================================================
+ * Copyright (C) 2024 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.cps.ncmp.impl.dmi;
+
+import lombok.AccessLevel;
+import lombok.NoArgsConstructor;
+import org.apache.commons.lang3.StringUtils;
+import org.onap.cps.ncmp.api.inventory.models.DmiPluginRegistration;
+import org.onap.cps.ncmp.api.inventory.models.NcmpServiceCmHandle;
+import org.onap.cps.ncmp.impl.inventory.models.YangModelCmHandle;
+import org.onap.cps.ncmp.impl.models.RequiredDmiService;
+
+@NoArgsConstructor(access = AccessLevel.PRIVATE)
+public class DmiServiceNameResolver {
+
+ /**
+ * Resolve a dmi service name.
+ *
+ * @param requiredService indicates what type of service is required
+ * @param yangModelCmHandle cm handle
+ * @return dmi service name
+ */
+ public static String resolveDmiServiceName(final RequiredDmiService requiredService,
+ final YangModelCmHandle yangModelCmHandle) {
+ return resolveDmiServiceName(requiredService,
+ yangModelCmHandle.getDmiServiceName(),
+ yangModelCmHandle.getDmiDataServiceName(),
+ yangModelCmHandle.getDmiModelServiceName());
+ }
+
+ /**
+ * Resolve a dmi service name.
+ *
+ * @param requiredService indicates what type of service is required
+ * @param ncmpServiceCmHandle cm handle
+ * @return dmi service name
+ */
+ public static String resolveDmiServiceName(final RequiredDmiService requiredService,
+ final NcmpServiceCmHandle ncmpServiceCmHandle) {
+ return resolveDmiServiceName(requiredService,
+ ncmpServiceCmHandle.getDmiServiceName(),
+ ncmpServiceCmHandle.getDmiDataServiceName(),
+ ncmpServiceCmHandle.getDmiModelServiceName());
+ }
+
+ /**
+ * Resolve a dmi service name.
+ *
+ * @param requiredService indicates what type of service is required
+ * @param dmiPluginRegistration dmi plugin registration
+ * @return dmi service name
+ */
+ public static String resolveDmiServiceName(final RequiredDmiService requiredService,
+ final DmiPluginRegistration dmiPluginRegistration) {
+ return resolveDmiServiceName(requiredService,
+ dmiPluginRegistration.getDmiPlugin(),
+ dmiPluginRegistration.getDmiDataPlugin(),
+ dmiPluginRegistration.getDmiModelPlugin());
+ }
+
+ private static String resolveDmiServiceName(final RequiredDmiService requiredService,
+ final String dmiServiceName,
+ final String dmiDataServiceName,
+ final String dmiModelServiceName) {
+ if (StringUtils.isBlank(dmiServiceName)) {
+ if (RequiredDmiService.DATA.equals(requiredService)) {
+ return dmiDataServiceName;
+ }
+ return dmiModelServiceName;
+ }
+ return dmiServiceName;
+ }
+
+}
diff --git a/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/inventory/AlternateIdChecker.java b/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/inventory/AlternateIdChecker.java
index 3600d6da32..8ebd456cda 100644
--- a/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/inventory/AlternateIdChecker.java
+++ b/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/inventory/AlternateIdChecker.java
@@ -28,6 +28,7 @@ import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.onap.cps.ncmp.api.inventory.models.NcmpServiceCmHandle;
+import org.onap.cps.ncmp.impl.inventory.models.YangModelCmHandle;
import org.onap.cps.spi.exceptions.DataNodeNotFoundException;
import org.springframework.stereotype.Service;
@@ -96,8 +97,8 @@ public class AlternateIdChecker {
.map(NcmpServiceCmHandle::getAlternateId)
.filter(StringUtils::isNotBlank)
.collect(Collectors.toSet());
- return inventoryPersistence.getCmHandleDataNodesByAlternateIds(alternateIdsToCheck).stream()
- .map(dataNode -> (String) dataNode.getLeaves().get("alternate-id"))
+ return inventoryPersistence.getYangModelCmHandleByAlternateIds(alternateIdsToCheck).stream()
+ .map(YangModelCmHandle::getAlternateId)
.collect(Collectors.toSet());
}
diff --git a/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/inventory/InventoryPersistence.java b/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/inventory/InventoryPersistence.java
index e5dd937cc0..e39da06514 100644
--- a/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/inventory/InventoryPersistence.java
+++ b/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/inventory/InventoryPersistence.java
@@ -130,20 +130,20 @@ public interface InventoryPersistence extends NcmpPersistence {
Collection<DataNode> getCmHandleDataNodeByCmHandleId(String cmHandleId);
/**
- * Get data node with the given alternate id.
+ * Get yang model cm handle with the given alternate id.
*
* @param alternateId alternate ID
- * @return data node
+ * @return yang model cm handle
*/
- DataNode getCmHandleDataNodeByAlternateId(String alternateId);
+ YangModelCmHandle getYangModelCmHandleByAlternateId(String alternateId);
/**
- * Get data nodes for the given batch of alternate ids.
+ * Get yang model cm handles for the given batch of alternate ids.
*
* @param alternateIds alternate IDs
- * @return data nodes
+ * @return yang model cm handles
*/
- Collection<DataNode> getCmHandleDataNodesByAlternateIds(Collection<String> alternateIds);
+ Collection<YangModelCmHandle> getYangModelCmHandleByAlternateIds(Collection<String> alternateIds);
/**
* Get collection of data nodes of given cm handles.
@@ -168,7 +168,7 @@ public interface InventoryPersistence extends NcmpPersistence {
* Check database if cm handle id exists if not return false.
*
* @param cmHandleId cmHandle Id
- * @return Boolean
+ * @return boolean
*/
- Boolean isExistingCmHandleId(String cmHandleId);
+ boolean isExistingCmHandleId(String cmHandleId);
}
diff --git a/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/inventory/InventoryPersistenceImpl.java b/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/inventory/InventoryPersistenceImpl.java
index e468ed100a..f8a38100aa 100644
--- a/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/inventory/InventoryPersistenceImpl.java
+++ b/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/inventory/InventoryPersistenceImpl.java
@@ -189,24 +189,25 @@ public class InventoryPersistenceImpl extends NcmpPersistenceImpl implements Inv
}
@Override
- public DataNode getCmHandleDataNodeByAlternateId(final String alternateId) {
+ public YangModelCmHandle getYangModelCmHandleByAlternateId(final String alternateId) {
final String cpsPathForCmHandleByAlternateId = getCpsPathForCmHandleByAlternateId(alternateId);
final Collection<DataNode> dataNodes = cmHandleQueryService
.queryNcmpRegistryByCpsPath(cpsPathForCmHandleByAlternateId, OMIT_DESCENDANTS);
if (dataNodes.isEmpty()) {
throw new CmHandleNotFoundException(alternateId);
}
- return dataNodes.iterator().next();
+ return YangDataConverter.toYangModelCmHandle(dataNodes.iterator().next());
}
@Override
- public Collection<DataNode> getCmHandleDataNodesByAlternateIds(final Collection<String> alternateIds) {
+ public Collection<YangModelCmHandle> getYangModelCmHandleByAlternateIds(final Collection<String> alternateIds) {
if (alternateIds.isEmpty()) {
return Collections.emptyList();
}
final String cpsPathForCmHandlesByAlternateIds = getCpsPathForCmHandlesByAlternateIds(alternateIds);
- return cmHandleQueryService.queryNcmpRegistryByCpsPath(cpsPathForCmHandlesByAlternateIds,
- INCLUDE_ALL_DESCENDANTS);
+ final Collection<DataNode> dataNodes = cmHandleQueryService.queryNcmpRegistryByCpsPath(
+ cpsPathForCmHandlesByAlternateIds, INCLUDE_ALL_DESCENDANTS);
+ return YangDataConverter.toYangModelCmHandles(dataNodes);
}
@Override
@@ -229,7 +230,7 @@ public class InventoryPersistenceImpl extends NcmpPersistenceImpl implements Inv
}
@Override
- public Boolean isExistingCmHandleId(final String cmHandleId) {
+ public boolean isExistingCmHandleId(final String cmHandleId) {
try {
return !getCmHandleDataNodeByCmHandleId(cmHandleId).isEmpty();
} catch (final DataNodeNotFoundException exception) {
diff --git a/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/inventory/models/YangModelCmHandle.java b/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/inventory/models/YangModelCmHandle.java
index 76ee286635..a262367e38 100644
--- a/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/inventory/models/YangModelCmHandle.java
+++ b/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/inventory/models/YangModelCmHandle.java
@@ -35,6 +35,7 @@ import lombok.Setter;
import org.apache.commons.lang3.StringUtils;
import org.onap.cps.ncmp.api.inventory.models.CompositeState;
import org.onap.cps.ncmp.api.inventory.models.NcmpServiceCmHandle;
+import org.onap.cps.ncmp.impl.dmi.DmiServiceNameResolver;
import org.onap.cps.ncmp.impl.models.RequiredDmiService;
/**
@@ -129,8 +130,7 @@ public class YangModelCmHandle {
yangModelCmHandle.setAlternateId(StringUtils.trimToEmpty(alternateId));
yangModelCmHandle.setDataProducerIdentifier(StringUtils.trimToEmpty(dataProducerIdentifier));
yangModelCmHandle.setDmiProperties(asYangModelCmHandleProperties(ncmpServiceCmHandle.getDmiProperties()));
- yangModelCmHandle.setPublicProperties(asYangModelCmHandleProperties(
- ncmpServiceCmHandle.getPublicProperties()));
+ yangModelCmHandle.setPublicProperties(asYangModelCmHandleProperties(ncmpServiceCmHandle.getPublicProperties()));
yangModelCmHandle.setCompositeState(ncmpServiceCmHandle.getCompositeState());
return yangModelCmHandle;
}
@@ -138,17 +138,11 @@ public class YangModelCmHandle {
/**
* Resolve a dmi service name.
*
- * @param requiredService indicates what typo of service is required
+ * @param requiredService indicates what type of service is required
* @return dmi service name
*/
public String resolveDmiServiceName(final RequiredDmiService requiredService) {
- if (StringUtils.isBlank(dmiServiceName)) {
- if (RequiredDmiService.DATA.equals(requiredService)) {
- return dmiDataServiceName;
- }
- return dmiModelServiceName;
- }
- return dmiServiceName;
+ return DmiServiceNameResolver.resolveDmiServiceName(requiredService, this);
}
private static List<Property> asYangModelCmHandleProperties(final Map<String, String> propertiesAsMap) {
diff --git a/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/inventory/trustlevel/TrustLevelManager.java b/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/inventory/trustlevel/TrustLevelManager.java
index a10e8ba308..b61e53854e 100644
--- a/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/inventory/trustlevel/TrustLevelManager.java
+++ b/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/inventory/trustlevel/TrustLevelManager.java
@@ -23,6 +23,7 @@ package org.onap.cps.ncmp.impl.inventory.trustlevel;
import com.hazelcast.map.IMap;
import java.util.Collection;
import java.util.Collections;
+import java.util.HashMap;
import java.util.Map;
import java.util.Set;
import java.util.stream.Collectors;
@@ -31,6 +32,7 @@ import lombok.extern.slf4j.Slf4j;
import org.onap.cps.ncmp.api.inventory.models.DmiPluginRegistration;
import org.onap.cps.ncmp.api.inventory.models.NcmpServiceCmHandle;
import org.onap.cps.ncmp.api.inventory.models.TrustLevel;
+import org.onap.cps.ncmp.impl.dmi.DmiServiceNameResolver;
import org.onap.cps.ncmp.impl.inventory.InventoryPersistence;
import org.onap.cps.ncmp.impl.inventory.models.YangModelCmHandle;
import org.onap.cps.ncmp.impl.models.RequiredDmiService;
@@ -60,12 +62,8 @@ public class TrustLevelManager {
* @param dmiPluginRegistration a dmi plugin being registered
*/
public void registerDmiPlugin(final DmiPluginRegistration dmiPluginRegistration) {
- final String dmiServiceName;
- if (DmiPluginRegistration.isNullEmptyOrBlank(dmiPluginRegistration.getDmiDataPlugin())) {
- dmiServiceName = dmiPluginRegistration.getDmiPlugin();
- } else {
- dmiServiceName = dmiPluginRegistration.getDmiDataPlugin();
- }
+ final String dmiServiceName = DmiServiceNameResolver.resolveDmiServiceName(RequiredDmiService.DATA,
+ dmiPluginRegistration);
trustLevelPerDmiPlugin.put(dmiServiceName, TrustLevel.COMPLETE);
}
@@ -146,9 +144,13 @@ public class TrustLevelManager {
public void applyEffectiveTrustLevels(final Collection<NcmpServiceCmHandle> ncmpServiceCmHandles) {
final Set<String> cmHandleIds = getCmHandleIds(ncmpServiceCmHandles);
final Map<String, TrustLevel> trustLevelPerCmHandleIdInBatch = trustLevelPerCmHandleId.getAll(cmHandleIds);
+ final Map<String, TrustLevel> trustLevelPerDmiPluginInBatch = new HashMap<>(trustLevelPerDmiPlugin);
for (final NcmpServiceCmHandle ncmpServiceCmHandle : ncmpServiceCmHandles) {
final String cmHandleId = ncmpServiceCmHandle.getCmHandleId();
- final TrustLevel dmiTrustLevel = TrustLevel.COMPLETE; // TODO: CPS-2375
+ final String dmiDataServiceName = DmiServiceNameResolver.resolveDmiServiceName(RequiredDmiService.DATA,
+ ncmpServiceCmHandle);
+ final TrustLevel dmiTrustLevel = trustLevelPerDmiPluginInBatch.getOrDefault(dmiDataServiceName,
+ TrustLevel.NONE);
final TrustLevel cmHandleTrustLevel = trustLevelPerCmHandleIdInBatch.getOrDefault(cmHandleId,
TrustLevel.NONE);
final TrustLevel effectiveTrustLevel = dmiTrustLevel.getEffectiveTrustLevel(cmHandleTrustLevel);
@@ -187,7 +189,7 @@ public class TrustLevelManager {
private String getDmiServiceName(final String cmHandleId) {
final YangModelCmHandle yangModelCmHandle = inventoryPersistence.getYangModelCmHandle(cmHandleId);
- return yangModelCmHandle.resolveDmiServiceName(RequiredDmiService.DATA);
+ return DmiServiceNameResolver.resolveDmiServiceName(RequiredDmiService.DATA, yangModelCmHandle);
}
private void sendAvcNotificationIfRequired(final String notificationCandidateCmHandleId,
diff --git a/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/utils/AlternateIdMatcher.java b/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/utils/AlternateIdMatcher.java
index 36c0cfa756..b97da2977a 100644
--- a/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/utils/AlternateIdMatcher.java
+++ b/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/utils/AlternateIdMatcher.java
@@ -21,15 +21,13 @@
package org.onap.cps.ncmp.impl.utils;
import lombok.RequiredArgsConstructor;
-import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.onap.cps.ncmp.api.exceptions.CmHandleNotFoundException;
import org.onap.cps.ncmp.exceptions.NoAlternateIdMatchFoundException;
import org.onap.cps.ncmp.impl.inventory.InventoryPersistence;
-import org.onap.cps.spi.model.DataNode;
+import org.onap.cps.ncmp.impl.inventory.models.YangModelCmHandle;
import org.springframework.stereotype.Service;
-@Slf4j
@Service
@RequiredArgsConstructor
public class AlternateIdMatcher {
@@ -37,19 +35,21 @@ public class AlternateIdMatcher {
private final InventoryPersistence inventoryPersistence;
/**
- * Get data node that matches longest alternate id by removing elements (as defined by the separator string)
- * from right to left. If alternate id contains a hash then all elements after that hash are ignored.
+ * Get yang model cm handle that matches longest alternate id by removing elements
+ * (as defined by the separator string) from right to left.
+ * If alternate id contains a hash then all elements after that hash are ignored.
*
* @param alternateId alternate ID
* @param separator a string that separates each element from the next.
- * @return data node
+ * @return yang model cm handle
*/
- public DataNode getCmHandleDataNodeByLongestMatchingAlternateId(final String alternateId, final String separator) {
+ public YangModelCmHandle getYangModelCmHandleByLongestMatchingAlternateId(final String alternateId,
+ final String separator) {
final String[] splitPath = alternateId.split("#", 2);
String bestMatch = splitPath[0];
while (StringUtils.isNotEmpty(bestMatch)) {
try {
- return inventoryPersistence.getCmHandleDataNodeByAlternateId(bestMatch);
+ return inventoryPersistence.getYangModelCmHandleByAlternateId(bestMatch);
} catch (final CmHandleNotFoundException ignored) {
bestMatch = getParentPath(bestMatch, separator);
}
@@ -67,8 +67,7 @@ public class AlternateIdMatcher {
if (inventoryPersistence.isExistingCmHandleId(cmHandleReference)) {
return cmHandleReference;
} else {
- return inventoryPersistence.getCmHandleDataNodeByAlternateId(cmHandleReference)
- .getLeaves().get("id").toString();
+ return inventoryPersistence.getYangModelCmHandleByAlternateId(cmHandleReference).getId();
}
}
diff --git a/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/utils/YangDataConverter.java b/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/utils/YangDataConverter.java
index ac0c44e1c3..1842107f44 100644
--- a/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/utils/YangDataConverter.java
+++ b/cps-ncmp-service/src/main/java/org/onap/cps/ncmp/impl/utils/YangDataConverter.java
@@ -47,12 +47,14 @@ public class YangDataConverter {
* @param yangModelCmHandle the yang model of the cm handle
* @return ncmp service cm handle
*/
- public static NcmpServiceCmHandle toNcmpServiceCmHandle(
- final YangModelCmHandle yangModelCmHandle) {
+ public static NcmpServiceCmHandle toNcmpServiceCmHandle(final YangModelCmHandle yangModelCmHandle) {
final NcmpServiceCmHandle ncmpServiceCmHandle = new NcmpServiceCmHandle();
final List<YangModelCmHandle.Property> dmiProperties = yangModelCmHandle.getDmiProperties();
final List<YangModelCmHandle.Property> publicProperties = yangModelCmHandle.getPublicProperties();
ncmpServiceCmHandle.setCmHandleId(yangModelCmHandle.getId());
+ ncmpServiceCmHandle.setDmiServiceName(yangModelCmHandle.getDmiServiceName());
+ ncmpServiceCmHandle.setDmiDataServiceName(yangModelCmHandle.getDmiDataServiceName());
+ ncmpServiceCmHandle.setDmiModelServiceName(yangModelCmHandle.getDmiModelServiceName());
ncmpServiceCmHandle.setCompositeState(yangModelCmHandle.getCompositeState());
ncmpServiceCmHandle.setModuleSetTag(yangModelCmHandle.getModuleSetTag());
ncmpServiceCmHandle.setAlternateId(yangModelCmHandle.getAlternateId());
diff --git a/cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/datajobs/WriteRequestExaminerSpec.groovy b/cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/datajobs/WriteRequestExaminerSpec.groovy
index 47b57669ca..6aa84d1c7f 100644
--- a/cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/datajobs/WriteRequestExaminerSpec.groovy
+++ b/cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/datajobs/WriteRequestExaminerSpec.groovy
@@ -1,3 +1,22 @@
+/*
+ * ============LICENSE_START=======================================================
+ * Copyright (C) 2024 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.cps.ncmp.impl.datajobs
@@ -6,7 +25,6 @@ import org.onap.cps.ncmp.api.datajobs.models.WriteOperation
import org.onap.cps.ncmp.api.inventory.models.NcmpServiceCmHandle
import org.onap.cps.ncmp.impl.inventory.models.YangModelCmHandle
import org.onap.cps.ncmp.impl.utils.AlternateIdMatcher
-import org.onap.cps.spi.model.DataNode
import spock.lang.Specification
class WriteRequestExaminerSpec extends Specification {
@@ -15,14 +33,14 @@ class WriteRequestExaminerSpec extends Specification {
def objectUnderTest = new WriteRequestExaminer(mockAlternateIdMatcher)
def setup() {
- def ch1 = new DataNode(leaves: [id: 'ch1', 'dmi-service-name': 'dmiA', 'data-producer-identifier': 'p1'])
- def ch2 = new DataNode(leaves: [id: 'ch2', 'dmi-service-name': 'dmiA', 'data-producer-identifier': 'p1'])
- def ch3 = new DataNode(leaves: [id: 'ch3', 'dmi-service-name': 'dmiA', 'data-producer-identifier': 'p2'])
- def ch4 = new DataNode(leaves: [id: 'ch4', 'dmi-service-name': 'dmiB', 'data-producer-identifier': 'p1'])
- mockAlternateIdMatcher.getCmHandleDataNodeByLongestMatchingAlternateId('fdn1', '/') >> ch1
- mockAlternateIdMatcher.getCmHandleDataNodeByLongestMatchingAlternateId('fdn2', '/') >> ch2
- mockAlternateIdMatcher.getCmHandleDataNodeByLongestMatchingAlternateId('fdn3', '/') >> ch3
- mockAlternateIdMatcher.getCmHandleDataNodeByLongestMatchingAlternateId('fdn4', '/') >> ch4
+ def ch1 = new YangModelCmHandle(id: 'ch1', dmiServiceName: 'dmiA', dataProducerIdentifier: 'p1', dmiProperties: [])
+ def ch2 = new YangModelCmHandle(id: 'ch2', dmiServiceName: 'dmiA', dataProducerIdentifier: 'p1', dmiProperties: [])
+ def ch3 = new YangModelCmHandle(id: 'ch3', dmiServiceName: 'dmiA', dataProducerIdentifier: 'p2', dmiProperties: [])
+ def ch4 = new YangModelCmHandle(id: 'ch4', dmiServiceName: 'dmiB', dataProducerIdentifier: 'p1', dmiProperties: [])
+ mockAlternateIdMatcher.getYangModelCmHandleByLongestMatchingAlternateId('fdn1', '/') >> ch1
+ mockAlternateIdMatcher.getYangModelCmHandleByLongestMatchingAlternateId('fdn2', '/') >> ch2
+ mockAlternateIdMatcher.getYangModelCmHandleByLongestMatchingAlternateId('fdn3', '/') >> ch3
+ mockAlternateIdMatcher.getYangModelCmHandleByLongestMatchingAlternateId('fdn4', '/') >> ch4
}
def 'Create a map of dmi write requests per producer key with #scenario.'() {
diff --git a/cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/inventory/AlternateIdCheckerSpec.groovy b/cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/inventory/AlternateIdCheckerSpec.groovy
index b976ff4284..087265b51f 100644
--- a/cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/inventory/AlternateIdCheckerSpec.groovy
+++ b/cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/inventory/AlternateIdCheckerSpec.groovy
@@ -23,7 +23,6 @@ package org.onap.cps.ncmp.impl.inventory
import org.onap.cps.ncmp.api.inventory.models.NcmpServiceCmHandle
import org.onap.cps.ncmp.impl.inventory.models.YangModelCmHandle
import org.onap.cps.spi.exceptions.DataNodeNotFoundException
-import org.onap.cps.spi.model.DataNode
import spock.lang.Specification
class AlternateIdCheckerSpec extends Specification {
@@ -37,8 +36,8 @@ class AlternateIdCheckerSpec extends Specification {
def batch = [new NcmpServiceCmHandle(cmHandleId: 'ch-1', alternateId: alt1),
new NcmpServiceCmHandle(cmHandleId: 'ch-2', alternateId: alt2)]
and: 'the database already contains cm handle(s) with these alternate ids: #altAlreadyInDb'
- mockInventoryPersistenceService.getCmHandleDataNodesByAlternateIds(_ as Collection<String>) >>
- { args -> args[0].stream().filter(altId -> altAlreadyInDb.contains(altId)).map(altId -> new DataNode(leaves: ["alternate-id": altId])).toList() }
+ mockInventoryPersistenceService.getYangModelCmHandleByAlternateIds(_ as Collection<String>) >>
+ { args -> args[0].stream().filter(altId -> altAlreadyInDb.contains(altId)).map(altId -> new YangModelCmHandle(alternateId: altId)).toList() }
when: 'the batch of new cm handles is checked'
def result = objectUnderTest.getIdsOfCmHandlesWithRejectedAlternateId(batch, AlternateIdChecker.Operation.CREATE)
then: 'the result contains ids of the rejected cm handles'
@@ -57,8 +56,8 @@ class AlternateIdCheckerSpec extends Specification {
given: 'a batch of 1 existing cm handle to update alternate id to #proposedAlt'
def batch = [new NcmpServiceCmHandle(cmHandleId: 'ch-1', alternateId: proposedAlt)]
and: 'the database already contains a cm handle with alternate id: #altAlreadyInDb'
- mockInventoryPersistenceService.getCmHandleDataNodesByAlternateIds(_ as Collection<String>) >>
- { args -> args[0].stream().filter(altId -> altAlreadyInDb == altId).map(altId -> new DataNode(leaves: ["alternate-id": altId])).toList() }
+ mockInventoryPersistenceService.getYangModelCmHandleByAlternateIds(_ as Collection<String>) >>
+ { args -> args[0].stream().filter(altId -> altAlreadyInDb == altId).map(altId -> new YangModelCmHandle(alternateId: altId)).toList() }
mockInventoryPersistenceService.getYangModelCmHandle(_) >> new YangModelCmHandle(alternateId: altAlreadyInDb)
when: 'the batch of cm handle updates is checked'
def result = objectUnderTest.getIdsOfCmHandlesWithRejectedAlternateId(batch, AlternateIdChecker.Operation.UPDATE)
@@ -75,7 +74,7 @@ class AlternateIdCheckerSpec extends Specification {
given: 'a batch of 1 non-existing cm handle to update alternate id'
def batch = [new NcmpServiceCmHandle(cmHandleId: 'non-existing', alternateId: 'altId')]
and: 'the database does not contain any cm handles'
- mockInventoryPersistenceService.getCmHandleDataNodesByAlternateIds(_) >> []
+ mockInventoryPersistenceService.getYangModelCmHandleByAlternateIds(_) >> []
mockInventoryPersistenceService.getYangModelCmHandle(_) >> { throwDataNodeNotFoundException() }
when: 'the batch of cm handle updates is checked'
def result = objectUnderTest.getIdsOfCmHandlesWithRejectedAlternateId(batch, AlternateIdChecker.Operation.UPDATE)
diff --git a/cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/inventory/InventoryPersistenceImplSpec.groovy b/cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/inventory/InventoryPersistenceImplSpec.groovy
index 4d8855c4b2..ab7ed98800 100644
--- a/cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/inventory/InventoryPersistenceImplSpec.groovy
+++ b/cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/inventory/InventoryPersistenceImplSpec.groovy
@@ -31,6 +31,7 @@ import org.onap.cps.ncmp.api.exceptions.CmHandleNotFoundException
import org.onap.cps.ncmp.api.inventory.models.CompositeState
import org.onap.cps.ncmp.impl.inventory.models.CmHandleState
import org.onap.cps.ncmp.impl.inventory.models.YangModelCmHandle
+import org.onap.cps.ncmp.impl.utils.YangDataConverter
import org.onap.cps.spi.CascadeDeleteAllowed
import org.onap.cps.spi.FetchDescendantsOption
import org.onap.cps.spi.model.DataNode
@@ -67,6 +68,8 @@ class InventoryPersistenceImplSpec extends Specification {
def mockCmHandleQueries = Mock(CmHandleQueryService)
+ def mockYangDataConverter = Mock(YangDataConverter)
+
def objectUnderTest = new InventoryPersistenceImpl(spiedJsonObjectMapper, mockCpsDataService, mockCpsModuleService,
mockCpsValidator, mockCpsAnchorService, mockCmHandleQueries)
@@ -312,29 +315,31 @@ class InventoryPersistenceImplSpec extends Specification {
1 * mockCpsDataService.getDataNodes(NCMP_DATASPACE_NAME, NCMP_DMI_REGISTRY_ANCHOR, expectedXPath, INCLUDE_ALL_DESCENDANTS)
}
- def 'Get cm handle data node by alternate id'() {
+ def 'Get yang model cm handle by alternate id'() {
given: 'expected xPath to get cmHandle data node'
def expectedXPath = '/dmi-registry/cm-handles[@alternate-id=\'alternate id\']'
+ def expectedDataNode = new DataNode(xpath: expectedXPath, leaves: [id: 'id', alternateId: 'alternate id'])
and: 'query service is invoked with expected xpath'
- mockCmHandleQueries.queryNcmpRegistryByCpsPath(expectedXPath, OMIT_DESCENDANTS) >> [new DataNode()]
- expect: 'getting the cm handle data node'
- assert objectUnderTest.getCmHandleDataNodeByAlternateId('alternate id') == new DataNode()
+ mockCmHandleQueries.queryNcmpRegistryByCpsPath(expectedXPath, OMIT_DESCENDANTS) >> [expectedDataNode]
+ mockYangDataConverter.toYangModelCmHandle(expectedDataNode) >> new YangModelCmHandle(id: 'id')
+ expect: 'getting the yang model cm handle'
+ assert objectUnderTest.getYangModelCmHandleByAlternateId('alternate id') == new YangModelCmHandle(id: 'id')
}
- def 'Attempt to get non existing cm handle data node by alternate id'() {
+ def 'Attempt to get non existing yang model cm handle by alternate id'() {
given: 'query service is invoked and returns empty collection of data nodes'
mockCmHandleQueries.queryNcmpRegistryByCpsPath(*_) >> []
- when: 'getting the cm handle data node'
- objectUnderTest.getCmHandleDataNodeByAlternateId('alternate id')
+ when: 'getting the yang model cm handle'
+ objectUnderTest.getYangModelCmHandleByAlternateId('alternate id')
then: 'no data found exception thrown'
def thrownException = thrown(CmHandleNotFoundException)
assert thrownException.getMessage().contains('Cm handle not found')
assert thrownException.getDetails().contains('No cm handles found with reference alternate id')
}
- def 'Get multiple cm handle data nodes by alternate ids, passing empty collection'() {
- when: 'getting the cm handle data node for no alternate ids'
- objectUnderTest.getCmHandleDataNodesByAlternateIds([])
+ def 'Get multiple yang model cm handles by alternate ids, passing empty collection'() {
+ when: 'getting the yang model cm handle for no alternate ids'
+ objectUnderTest.getYangModelCmHandleByAlternateIds([])
then: 'query service is not invoked'
0 * mockCmHandleQueries.queryNcmpRegistryByCpsPath(_, _)
}
diff --git a/cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/inventory/trustlevel/TrustLevelManagerSpec.groovy b/cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/inventory/trustlevel/TrustLevelManagerSpec.groovy
index bf79fe35d3..1088ca8e06 100644
--- a/cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/inventory/trustlevel/TrustLevelManagerSpec.groovy
+++ b/cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/inventory/trustlevel/TrustLevelManagerSpec.groovy
@@ -177,25 +177,23 @@ class TrustLevelManagerSpec extends Specification {
def ncmpServiceCmHandle = new NcmpServiceCmHandle(cmHandleId: 'ch-1')
when: 'effective trust level selected'
objectUnderTest.applyEffectiveTrustLevel(ncmpServiceCmHandle)
- then: 'effective trust level is trusted'
- // FIXME CPS-2375: the expected behaviour is to return the lower TrustLevel (NONE)
- assert ncmpServiceCmHandle.currentTrustLevel == TrustLevel.COMPLETE
+ then: 'effective trust level is none'
+ assert ncmpServiceCmHandle.currentTrustLevel == TrustLevel.NONE
}
def 'Apply effective trust levels from CmHandle batch'() {
- given: 'a non trusted dmi'
- trustLevelPerDmiPlugin.put('my-dmi', TrustLevel.NONE)
+ given: 'a trusted dmi'
+ trustLevelPerDmiPlugin.put('my-dmi', TrustLevel.COMPLETE)
and: 'a trusted CmHandle'
trustLevelPerCmHandleId.put('ch-1', TrustLevel.COMPLETE)
and: 'a not trusted CmHandle'
trustLevelPerCmHandleId.put('ch-2', TrustLevel.NONE)
and: 'cm handle objects'
- def ncmpServiceCmHandle1 = new NcmpServiceCmHandle(cmHandleId: 'ch-1')
- def ncmpServiceCmHandle2 = new NcmpServiceCmHandle(cmHandleId: 'ch-2')
+ def ncmpServiceCmHandle1 = new NcmpServiceCmHandle(cmHandleId: 'ch-1', dmiServiceName: 'my-dmi')
+ def ncmpServiceCmHandle2 = new NcmpServiceCmHandle(cmHandleId: 'ch-2', dmiDataServiceName: 'my-dmi')
when: 'effective trust level selected'
objectUnderTest.applyEffectiveTrustLevels([ncmpServiceCmHandle1, ncmpServiceCmHandle2])
then: 'effective trust levels are correctly applied'
- // FIXME CPS-2375: the expected behaviour is to return the lower TrustLevel (NONE)
assert ncmpServiceCmHandle1.currentTrustLevel == TrustLevel.COMPLETE
assert ncmpServiceCmHandle2.currentTrustLevel == TrustLevel.NONE
}
diff --git a/cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/utils/AlternateIdMatcherSpec.groovy b/cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/utils/AlternateIdMatcherSpec.groovy
index 0a58039d8a..a6d21afd30 100644
--- a/cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/utils/AlternateIdMatcherSpec.groovy
+++ b/cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/utils/AlternateIdMatcherSpec.groovy
@@ -23,7 +23,7 @@ package org.onap.cps.ncmp.impl.utils
import org.onap.cps.ncmp.api.exceptions.CmHandleNotFoundException
import org.onap.cps.ncmp.exceptions.NoAlternateIdMatchFoundException
import org.onap.cps.ncmp.impl.inventory.InventoryPersistence
-import org.onap.cps.spi.model.DataNode
+import org.onap.cps.ncmp.impl.inventory.models.YangModelCmHandle
import spock.lang.Specification
class AlternateIdMatcherSpec extends Specification {
@@ -33,14 +33,14 @@ class AlternateIdMatcherSpec extends Specification {
def setup() {
given: 'cm handle in the registry with alternate id /a/b'
- mockInventoryPersistence.getCmHandleDataNodeByAlternateId('/a/b') >> new DataNode()
+ mockInventoryPersistence.getYangModelCmHandleByAlternateId('/a/b') >> new YangModelCmHandle()
and: 'no other cm handle'
- mockInventoryPersistence.getCmHandleDataNodeByAlternateId(_) >> { throw new CmHandleNotFoundException('') }
+ mockInventoryPersistence.getYangModelCmHandleByAlternateId(_) >> { throw new CmHandleNotFoundException('') }
}
def 'Finding longest alternate id matches.'() {
expect: 'querying for alternate id a matching result found'
- assert objectUnderTest.getCmHandleDataNodeByLongestMatchingAlternateId(targetAlternateId, '/') != null
+ assert objectUnderTest.getYangModelCmHandleByLongestMatchingAlternateId(targetAlternateId, '/') != null
where: 'the following parameters are used'
scenario | targetAlternateId
'exact match' | '/a/b'
@@ -55,7 +55,7 @@ class AlternateIdMatcherSpec extends Specification {
def 'Attempt to find longest alternate id match without any matches.'() {
when: 'attempt to find alternateId'
- objectUnderTest.getCmHandleDataNodeByLongestMatchingAlternateId(targetAlternateId, '/')
+ objectUnderTest.getYangModelCmHandleByLongestMatchingAlternateId(targetAlternateId, '/')
then: 'no alternate id match found exception thrown'
def thrown = thrown(NoAlternateIdMatchFoundException)
and: 'the exception has the relevant details from the error response'
@@ -73,12 +73,12 @@ class AlternateIdMatcherSpec extends Specification {
def result = objectUnderTest.getCmHandleId(cmHandleReference)
then: 'the inventory persistence service returns a cm handle (or not)'
mockInventoryPersistence.isExistingCmHandleId(cmHandleReference) >> existingCmHandleIdResponse
- mockInventoryPersistence.getCmHandleDataNodeByAlternateId(cmHandleReference) >> alternateIdGetResponse
+ mockInventoryPersistence.getYangModelCmHandleByAlternateId(cmHandleReference) >> alternateIdGetResponse
and: 'correct result is returned'
assert result == cmHandleReference
- where:
+ where: 'the following parameters are used'
cmHandleReference | existingCmHandleIdResponse | alternateIdGetResponse
'ch-1' | true | ''
- 'alt-1' | false | new DataNode(leaves: [id:'alt-1'])
+ 'alt-1' | false | new YangModelCmHandle(id: 'alt-1')
}
}
diff --git a/cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/utils/YangDataConverterSpec.groovy b/cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/utils/YangDataConverterSpec.groovy
index bb45e8ad96..1b8a33fea9 100644
--- a/cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/utils/YangDataConverterSpec.groovy
+++ b/cps-ncmp-service/src/test/groovy/org/onap/cps/ncmp/impl/utils/YangDataConverterSpec.groovy
@@ -31,11 +31,15 @@ class YangDataConverterSpec extends Specification{
leaves: ['name': 'dmiProp1', 'value': 'dmiValue1'])
def dataNodePublicProperties = new DataNode(xpath:'/public-properties[@name="pubProp1"]',
leaves: ['name': 'pubProp1', 'value': 'pubValue1'])
- def dataNodeCmHandle = new DataNode(leaves:['id':'sample-id'], childDataNodes:[dataNodeAdditionalProperties, dataNodePublicProperties])
+ def dataNodeCmHandle = new DataNode(leaves:['id':'sample-id', 'alternate-id': 'alt-id', 'module-set-tag': 'my-tag', 'dmi-service-name': 'my-dmi', 'data-producer-identifier': 'my-dpi'], childDataNodes:[dataNodeAdditionalProperties, dataNodePublicProperties])
when: 'the dataNode is converted'
def yangModelCmHandle = YangDataConverter.toYangModelCmHandle(dataNodeCmHandle)
- then: 'the converted object has the correct id'
+ then: 'the converted object has the fields'
assert yangModelCmHandle.id == 'sample-id'
+ assert yangModelCmHandle.alternateId == 'alt-id'
+ assert yangModelCmHandle.dmiServiceName == 'my-dmi'
+ assert yangModelCmHandle.moduleSetTag == 'my-tag'
+ assert yangModelCmHandle.dataProducerIdentifier == 'my-dpi'
and: 'the additional (dmi, private) properties are included'
assert yangModelCmHandle.dmiProperties[0].name == 'dmiProp1'
assert yangModelCmHandle.dmiProperties[0].value == 'dmiValue1'
diff --git a/cps-service/src/main/java/org/onap/cps/api/CpsQueryService.java b/cps-service/src/main/java/org/onap/cps/api/CpsQueryService.java
index edd2d2ad32..34dcbb9e32 100644
--- a/cps-service/src/main/java/org/onap/cps/api/CpsQueryService.java
+++ b/cps-service/src/main/java/org/onap/cps/api/CpsQueryService.java
@@ -1,6 +1,6 @@
/*
* ============LICENSE_START=======================================================
- * Copyright (C) 2020-2022 Nordix Foundation
+ * Copyright (C) 2020-2024 Nordix Foundation
* Modifications Copyright (C) 2022-2023 TechMahindra Ltd.
* ================================================================================
* Licensed under the Apache License, Version 2.0 (the "License");
@@ -22,6 +22,7 @@
package org.onap.cps.api;
import java.util.Collection;
+import java.util.Set;
import org.onap.cps.spi.FetchDescendantsOption;
import org.onap.cps.spi.PaginationOption;
import org.onap.cps.spi.model.DataNode;
@@ -44,6 +45,18 @@ public interface CpsQueryService {
Collection<DataNode> queryDataNodes(String dataspaceName, String anchorName,
String cpsPath, FetchDescendantsOption fetchDescendantsOption);
+
+ /**
+ * Get data leaf for the given dataspace and anchor by cps path.
+ *
+ * @param dataspaceName dataspace name
+ * @param anchorName anchor name
+ * @param cpsPath cps path
+ * @param targetClass class of the expected data type
+ * @return a collection of data objects of expected type
+ */
+ <T> Set<T> queryDataLeaf(String dataspaceName, String anchorName, String cpsPath, Class<T> targetClass);
+
/**
* Get data nodes for the given dataspace across all anchors by cps path.
*
diff --git a/cps-service/src/main/java/org/onap/cps/api/impl/CpsQueryServiceImpl.java b/cps-service/src/main/java/org/onap/cps/api/impl/CpsQueryServiceImpl.java
index d1c98986e6..1de7c1733e 100644
--- a/cps-service/src/main/java/org/onap/cps/api/impl/CpsQueryServiceImpl.java
+++ b/cps-service/src/main/java/org/onap/cps/api/impl/CpsQueryServiceImpl.java
@@ -1,6 +1,6 @@
/*
* ============LICENSE_START=======================================================
- * Copyright (C) 2021-2022 Nordix Foundation
+ * Copyright (C) 2021-2024 Nordix Foundation
* Modifications Copyright (C) 2022-2023 TechMahindra Ltd.
* ================================================================================
* Licensed under the Apache License, Version 2.0 (the "License");
@@ -23,6 +23,7 @@ package org.onap.cps.api.impl;
import io.micrometer.core.annotation.Timed;
import java.util.Collection;
+import java.util.Set;
import lombok.RequiredArgsConstructor;
import org.onap.cps.api.CpsQueryService;
import org.onap.cps.impl.utils.CpsValidator;
@@ -43,15 +44,23 @@ public class CpsQueryServiceImpl implements CpsQueryService {
@Timed(value = "cps.data.service.datanode.query",
description = "Time taken to query data nodes")
public Collection<DataNode> queryDataNodes(final String dataspaceName, final String anchorName,
- final String cpsPath, final FetchDescendantsOption fetchDescendantsOption) {
+ final String cpsPath,
+ final FetchDescendantsOption fetchDescendantsOption) {
cpsValidator.validateNameCharacters(dataspaceName, anchorName);
return cpsDataPersistenceService.queryDataNodes(dataspaceName, anchorName, cpsPath, fetchDescendantsOption);
}
@Override
- public Collection<DataNode> queryDataNodesAcrossAnchors(final String dataspaceName,
- final String cpsPath, final FetchDescendantsOption fetchDescendantsOption,
- final PaginationOption paginationOption) {
+ public <T> Set<T> queryDataLeaf(final String dataspaceName, final String anchorName, final String cpsPath,
+ final Class<T> targetClass) {
+ cpsValidator.validateNameCharacters(dataspaceName, anchorName);
+ throw new UnsupportedOperationException("Query by attribute-axis not implemented yet!");
+ }
+
+ @Override
+ public Collection<DataNode> queryDataNodesAcrossAnchors(final String dataspaceName, final String cpsPath,
+ final FetchDescendantsOption fetchDescendantsOption,
+ final PaginationOption paginationOption) {
cpsValidator.validateNameCharacters(dataspaceName);
cpsValidator.validatePaginationOption(paginationOption);
return cpsDataPersistenceService.queryDataNodesAcrossAnchors(dataspaceName, cpsPath,
diff --git a/cps-service/src/test/groovy/org/onap/cps/api/impl/CpsQueryServiceImplSpec.groovy b/cps-service/src/test/groovy/org/onap/cps/api/impl/CpsQueryServiceImplSpec.groovy
index 3b10669ddb..74127e095f 100644
--- a/cps-service/src/test/groovy/org/onap/cps/api/impl/CpsQueryServiceImplSpec.groovy
+++ b/cps-service/src/test/groovy/org/onap/cps/api/impl/CpsQueryServiceImplSpec.groovy
@@ -71,4 +71,12 @@ class CpsQueryServiceImplSpec extends Specification {
then: 'the persistence service is called once with the correct parameters'
1 * mockCpsDataPersistenceService.countAnchorsForDataspaceAndCpsPath("some-dataspace", "/cps-path")
}
+
+ // TODO will be implemented in CPS-2416
+ def 'Query data leaf.'() {
+ when: 'a query for a specific leaf is executed'
+ objectUnderTest.queryDataLeaf('some-dataspace', 'some-anchor', '/cps-path/@id', Object.class)
+ then: 'solution is not implemented yet'
+ thrown(UnsupportedOperationException)
+ }
}
diff --git a/integration-test/src/test/groovy/org/onap/cps/integration/functional/cps/QueryServiceIntegrationSpec.groovy b/integration-test/src/test/groovy/org/onap/cps/integration/functional/cps/QueryServiceIntegrationSpec.groovy
index 3b49cfc415..23e41c4178 100644
--- a/integration-test/src/test/groovy/org/onap/cps/integration/functional/cps/QueryServiceIntegrationSpec.groovy
+++ b/integration-test/src/test/groovy/org/onap/cps/integration/functional/cps/QueryServiceIntegrationSpec.groovy
@@ -27,6 +27,7 @@ import org.onap.cps.integration.base.FunctionalSpecBase
import org.onap.cps.spi.FetchDescendantsOption
import org.onap.cps.spi.PaginationOption
import org.onap.cps.spi.exceptions.CpsPathException
+import spock.lang.Ignore
import static org.onap.cps.spi.FetchDescendantsOption.DIRECT_CHILDREN_ONLY
import static org.onap.cps.spi.FetchDescendantsOption.INCLUDE_ALL_DESCENDANTS
@@ -56,6 +57,44 @@ class QueryServiceIntegrationSpec extends FunctionalSpecBase {
'the AND is used where result does not exist' | '//books[@lang="English" and @price=1000]' || 0 | []
}
+ @Ignore // TODO will be implemented in CPS-2416
+ def 'Query data leaf using CPS path for #scenario.'() {
+ when: 'query data leaf for bookstore container'
+ def result = objectUnderTest.queryDataLeaf(FUNCTIONAL_TEST_DATASPACE_1, BOOKSTORE_ANCHOR_1, cpsPath, Object.class)
+ then: 'the result contains the expected number of leaf values'
+ assert result.size() == expectedUniqueBooksTitles
+ where:
+ scenario | cpsPath || expectedUniqueBooksTitles
+ 'all books' | '//books/@title' || 19
+ 'all books in a category' | '/bookstore/categories[@code=5]/books/@title' || 10
+ 'non-existing path' | '/non-existing/@title' || 0
+ }
+
+ @Ignore
+ def 'Query data leaf with type #leafType using CPS path.'() {
+ given: 'a cps path query for two books, returning only #leafName'
+ def cpsPath = '//books[@title="Matilda" or @title="Good Omens"]/@' + leafName
+ when: 'query data leaf for bookstore container'
+ def results = objectUnderTest.queryDataLeaf(FUNCTIONAL_TEST_DATASPACE_1, BOOKSTORE_ANCHOR_1, cpsPath, leafType)
+ then: 'the result contains the expected leaf values'
+ assert results == expectedResults as Set
+ where:
+ leafName | leafType || expectedResults
+ 'lang' | String.class || ['English']
+ 'price' | Number.class || [13, 20]
+ 'editions' | List.class || [[1988, 2000], [2006]]
+ }
+
+ @Ignore
+ def 'Query data leaf using CPS path with ancestor axis.'() {
+ given: 'a cps path query that will return the names of the categories of two books'
+ def cpsPath = '//books[@title="Matilda" or @title="Good Omens"]/ancestor::categories/@name'
+ when: 'query data leaf for bookstore container'
+ def result = objectUnderTest.queryDataLeaf(FUNCTIONAL_TEST_DATASPACE_1, BOOKSTORE_ANCHOR_1, cpsPath, String.class)
+ then: 'the result contains the expected leaf values'
+ assert result == ['Children', 'Comedy'] as Set
+ }
+
def 'Cps Path query using comparative and boolean operators.'() {
given: 'a cps path query in the discount category'
def cpsPath = "/bookstore/categories[@code='5']/books" + leafCondition
diff --git a/integration-test/src/test/groovy/org/onap/cps/integration/performance/ncmp/CmHandleQueryByAlternateIdPerfTest.groovy b/integration-test/src/test/groovy/org/onap/cps/integration/performance/ncmp/CmHandleQueryByAlternateIdPerfTest.groovy
index a2d3a4aeac..b00893b718 100644
--- a/integration-test/src/test/groovy/org/onap/cps/integration/performance/ncmp/CmHandleQueryByAlternateIdPerfTest.groovy
+++ b/integration-test/src/test/groovy/org/onap/cps/integration/performance/ncmp/CmHandleQueryByAlternateIdPerfTest.groovy
@@ -41,7 +41,7 @@ class CmHandleQueryByAlternateIdPerfTest extends NcmpPerfTestBase {
when: 'an alternate id as cps path query'
resourceMeter.start()
def cpsPath = "/a/b/c/d-5/e/f/g/h/i"
- def dataNodes = objectUnderTest.getCmHandleDataNodeByLongestMatchingAlternateId(cpsPath, '/')
+ def dataNodes = objectUnderTest.getYangModelCmHandleByLongestMatchingAlternateId(cpsPath, '/')
and: 'the ids of the result are extracted and converted to xpath'
def cpsXpaths = dataNodes.stream().map(dataNode -> "/dmi-registry/cm-handles[@id='${dataNode.leaves.id}']".toString() ).collect(Collectors.toSet())
and: 'a single get is executed to get all the parent objects and their descendants'