29722563f4a7d943b19c96ca5fbf894773569f5b
[vid.git] / vid-app-common / src / test / java / org / onap / vid / services / AAITreeNodesEnricherTest.java
1 /*-
2  * ============LICENSE_START=======================================================
3  * VID
4  * ================================================================================
5  * Copyright (C) 2017 - 2020 AT&T Intellectual Property. All rights reserved.
6  * ================================================================================
7  * Licensed under the Apache License, Version 2.0 (the "License");
8  * you may not use this file except in compliance with the License.
9  * You may obtain a copy of the License at
10  * 
11  *      http://www.apache.org/licenses/LICENSE-2.0
12  * 
13  * Unless required by applicable law or agreed to in writing, software
14  * distributed under the License is distributed on an "AS IS" BASIS,
15  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16  * See the License for the specific language governing permissions and
17  * limitations under the License.
18  * ============LICENSE_END=========================================================
19  */
20
21 package org.onap.vid.services;
22
23 import static java.util.Collections.emptyList;
24 import static java.util.Collections.emptyMap;
25 import static java.util.stream.Collectors.toList;
26 import static net.javacrumbs.jsonunit.JsonMatchers.jsonEquals;
27 import static org.hamcrest.MatcherAssert.assertThat;
28 import static org.hamcrest.collection.IsIterableContainingInAnyOrder.containsInAnyOrder;
29 import static org.mockito.Matchers.any;
30 import static org.mockito.Mockito.mock;
31 import static org.mockito.Mockito.when;
32
33 import com.google.common.collect.ImmutableList;
34 import com.google.common.collect.ImmutableMap;
35 import com.google.common.collect.Streams;
36 import java.util.Collection;
37 import java.util.List;
38 import net.javacrumbs.jsonunit.core.Option;
39 import org.apache.commons.lang3.builder.ReflectionToStringBuilder;
40 import org.apache.commons.lang3.builder.ToStringStyle;
41 import org.jetbrains.annotations.NotNull;
42 import org.mockito.InjectMocks;
43 import org.mockito.Mock;
44 import org.onap.vid.aai.AaiClientInterface;
45 import org.onap.vid.aai.model.ModelVer;
46 import org.onap.vid.asdc.parser.ServiceModelInflator;
47 import org.onap.vid.asdc.parser.ServiceModelInflator.Names;
48 import org.onap.vid.exceptions.GenericUncheckedException;
49 import org.onap.vid.model.ServiceModel;
50 import org.onap.vid.model.aaiTree.AAITreeNode;
51 import org.onap.vid.model.aaiTree.NodeType;
52 import org.onap.vid.properties.Features;
53 import org.onap.vid.testUtils.TestUtils;
54 import org.testng.annotations.BeforeMethod;
55 import org.testng.annotations.DataProvider;
56 import org.testng.annotations.Test;
57 import org.togglz.core.manager.FeatureManager;
58
59 public class AAITreeNodesEnricherTest {
60
61     @Mock
62     private AaiClientInterface aaiClient;
63     @Mock
64     private VidService sdcService;
65     @Mock
66     private ServiceModelInflator serviceModelInflator;
67     @Mock
68     private FeatureManager featureManager;
69     @InjectMocks
70     private AAITreeNodesEnricher aaiTreeNodesEnricher;
71
72     @BeforeMethod
73     public void initMocks() {
74         TestUtils.initMockitoMocks(this);
75     }
76
77     private final static String nullString = "null placeholder";
78
79     @Test
80     public void enrichNodesWithModelCustomizationName_simple3NodesCase_nodesEnriched() {
81
82         when(serviceModelInflator.toNamesByVersionId(any())).thenReturn(ImmutableMap.of(
83                 "version id a", new Names("name a", "key a"),
84                 "version id b", new Names("name b", "key b"),
85                 "version id c", new Names("name c", "key c")
86         ));
87
88         final ImmutableList<String> versionIds = ImmutableList.of("version id a", "version id b", "version id c");
89         final ImmutableList<Names> expectedNames = ImmutableList.of(
90                 new Names("name a", "key a"),
91                 new Names("name b", "key b"),
92                 new Names("name c", "key c"));
93
94
95         final List<AAITreeNode> nodesUnderTest = nodesWithVersionIds(versionIds);
96         aaiTreeNodesEnricher.enrichNodesWithModelCustomizationName(nodesUnderTest, null);
97
98         assertThat(toStrings(nodesUnderTest), containsInAnyOrder(toStringsArray(nodesWithVersionIdsAndCustomizationNames(versionIds, expectedNames))));
99     }
100
101     @Test
102     public void enrichNodesWithModelCustomizationName_noNodes_noError() {
103
104         when(serviceModelInflator.toNamesByVersionId(any())).thenReturn(ImmutableMap.of(
105                 "11c6dc3e-cd6a-41b3-a50e-b5a10f7157d0", new Names("my model cust name", "my key")
106         ));
107
108         aaiTreeNodesEnricher.enrichNodesWithModelCustomizationName(emptyList(), null);
109     }
110
111     @Test
112     public void enrichNodesWithModelCustomizationName_nothingInModel_nodesUnchanged() {
113
114         when(serviceModelInflator.toNamesByVersionId(any())).thenReturn(emptyMap());
115
116         final ImmutableList<String> versionIds = ImmutableList.of("version id a", "version id b", "version id c");
117         final Names nullNames = new Names(nullString, nullString);
118         final ImmutableList<Names> expectedNames = ImmutableList.of(nullNames, nullNames, nullNames);
119
120         
121         final List<AAITreeNode> nodesUnderTest = nodesWithVersionIds(versionIds);
122
123         aaiTreeNodesEnricher.enrichNodesWithModelCustomizationName(nodesUnderTest, null);
124
125         assertThat(toStrings(nodesUnderTest), containsInAnyOrder(toStringsArray(nodesWithVersionIdsAndCustomizationNames(versionIds, expectedNames))));
126     }
127
128     @Test
129     public void enrichNodesWithModelCustomizationName_staggered4NodesAndNull_3nodesEnriched2isNull() {
130
131         when(serviceModelInflator.toNamesByVersionId(any())).thenReturn(ImmutableMap.of(
132                 "version id Z", new Names("name Z", "key Z"),
133                 "version id d", new Names(null, "key d"),
134                 "version id c", new Names("name c", null),
135                 "version id a", new Names("name a", "key a")
136         ));
137
138         final ImmutableList<String> versionIds = ImmutableList.of("version id a", "version id b", "version id c", "version id d", nullString);
139         final ImmutableList<Names> expectedNames = ImmutableList.of(
140                 new Names("name a", "key a"),
141                 new Names(nullString, nullString),
142                 new Names("name c", nullString),
143                 new Names(nullString, "key d"),
144                 new Names(nullString, nullString)
145         );
146
147
148         final List<AAITreeNode> nodesUnderTest = nodesWithVersionIds(versionIds);
149
150         aaiTreeNodesEnricher.enrichNodesWithModelCustomizationName(nodesUnderTest, null);
151
152         assertThat(toStrings(nodesUnderTest), containsInAnyOrder(toStringsArray(nodesWithVersionIdsAndCustomizationNames(versionIds, expectedNames))));
153     }
154
155     @DataProvider
156     public static Object[][] enrichVfModulesFilteredOutCases() {
157         AAITreeNode volumeGroup = new AAITreeNode();
158         volumeGroup.setType(NodeType.VOLUME_GROUP);
159
160         AAITreeNode vfModuleWithoutData = new AAITreeNode();
161         vfModuleWithoutData.setType(NodeType.VF_MODULE);
162
163         AAITreeNode vfModuleWithModelCustomizationName = new AAITreeNode();
164         vfModuleWithModelCustomizationName.setType(NodeType.VF_MODULE);
165         vfModuleWithModelCustomizationName.setModelCustomizationName("foo");
166
167         AAITreeNode vfModuleWithKeyInModel = new AAITreeNode();
168         vfModuleWithKeyInModel.setType(NodeType.VF_MODULE);
169         vfModuleWithKeyInModel.setKeyInModel("foo");
170
171         return new Object[][]{
172             {"no nodes", null, true},
173             {"no vfmodules", volumeGroup, true},
174             {"flag is off", vfModuleWithoutData, false},
175             {"all vfmodules with either getKeyInModel or getModelCustomizationId", vfModuleWithModelCustomizationName, true},
176             {"all vfmodules with either getKeyInModel or getModelCustomizationId", vfModuleWithKeyInModel, true},
177         };
178     }
179
180     @Test(dataProvider = "enrichVfModulesFilteredOutCases")
181     public void enrichVfModulesWithModelCustomizationNameFromOtherVersions_givenFilteredOutCases_doNothing(String reasonToSkip, AAITreeNode node, boolean flagState) {
182         when(featureManager.isActive(Features.FLAG_EXP_TOPOLOGY_TREE_VFMODULE_NAMES_FROM_OTHER_TOSCA_VERSIONS))
183             .thenReturn(flagState);
184
185         when(aaiClient.getSortedVersionsByInvariantId(any()))
186             .thenThrow(new AssertionError("did not expect reaching getSortedVersionsByInvariantId"));
187
188         List<AAITreeNode> nodes = (node == null) ? emptyList() : ImmutableList.of(node);
189         aaiTreeNodesEnricher.enrichVfModulesWithModelCustomizationNameFromOtherVersions(nodes, "modelInvariantId");
190     }
191
192     @FunctionalInterface
193     public interface Creator<T, R> {
194         R by(T t);
195     }
196
197     @Test
198     public void enrichVfModulesWithModelCustomizationNameFromOtherVersions() {
199         /*
200         Verifies the following
201
202         [*] aaiClient.getSortedVersionsByInvariantId response is exhausted
203             and all models fetched from sdc
204             -> we can see that model #1 info is populated in nodes
205         [*] relevant nodes enriched
206         [*] where data not found: nodes not enriched
207         [*] where data there already: node left pristine
208         [*] where node is not vfmodule: node left pristine
209
210          */
211
212         String modelInvariantId = "modelInvariantId";
213
214         ///////////// HELPERS
215
216         Creator<Integer, AAITreeNode> nodeMissingData = n -> {
217             AAITreeNode node = new AAITreeNode();
218             node.setType(NodeType.VF_MODULE);
219             node.setModelCustomizationId("model-customization-id-" + n);
220             return node;
221         };
222
223         Creator<Integer, AAITreeNode> nodeWithData = n -> {
224             AAITreeNode node = nodeMissingData.by(n);
225             node.setModelCustomizationName("modelCustomizationName-" + n);
226             node.setKeyInModel("modelKey-" + n);
227             return node;
228         };
229
230         Creator<Integer, ImmutableMap<String, Names>> namesMap = n -> ImmutableMap.of(
231             "model-customization-id-" + n,
232             new Names("modelCustomizationName-" + n, "modelKey-" + n)
233         );
234
235         Creator<Integer, ModelVer> modelVer = n -> {
236             ModelVer m = new ModelVer();
237             m.setModelVersion("model-version-" + n);
238             m.setModelVersionId("model-version-id-" + n);
239             return m;
240         };
241
242         ///////////// SET-UP
243
244         when(featureManager.isActive(Features.FLAG_EXP_TOPOLOGY_TREE_VFMODULE_NAMES_FROM_OTHER_TOSCA_VERSIONS))
245             .thenReturn(true);
246
247         /*
248         +-------------+----------+----------+----------+-----------+-----------+
249         |             | model v1 | model v2 | model v3 | model v77 | model v99 |
250         +-------------+----------+----------+----------+-----------+-----------+
251         | in AAI list |   v      |   v      |   v      |   v       |           |
252         | in SDC      |   v      |   v      |   v      |           |           |
253         | in nodes    |   v      |          |   v      |   v       |   v       |
254         +-------------+----------+----------+----------+-----------+-----------+
255          */
256         when(aaiClient.getSortedVersionsByInvariantId(modelInvariantId))
257             .thenReturn(ImmutableList.of(modelVer.by(3), modelVer.by(77), modelVer.by(2), modelVer.by(1)));
258
259         ServiceModel serviceModel_1 = mock(ServiceModel.class);
260         when(sdcService.getServiceModelOrThrow("model-version-id-1")).thenReturn(serviceModel_1);
261         when(serviceModelInflator.toNamesByCustomizationId(serviceModel_1)).thenReturn(namesMap.by(1));
262
263         ServiceModel serviceModel_2 = mock(ServiceModel.class);
264         when(sdcService.getServiceModelOrThrow("model-version-id-2")).thenReturn(serviceModel_2);
265         when(serviceModelInflator.toNamesByCustomizationId(serviceModel_2)).thenReturn(namesMap.by(2));
266
267         ServiceModel serviceModel_3 = mock(ServiceModel.class);
268         when(sdcService.getServiceModelOrThrow("model-version-id-3")).thenReturn(serviceModel_3);
269         when(serviceModelInflator.toNamesByCustomizationId(serviceModel_3)).thenReturn(namesMap.by(3));
270
271         when(sdcService.getServiceModelOrThrow("model-version-id-77")).thenThrow(GenericUncheckedException.class);
272
273         AAITreeNode nodeWithDataAlready = nodeMissingData.by(1);
274         nodeWithDataAlready.setModelCustomizationName("significant-customization-name");
275         nodeWithDataAlready.setKeyInModel("significant-key-in-model");
276
277         AAITreeNode nodeNotVfModule = nodeMissingData.by(1);
278         nodeNotVfModule.setType(NodeType.GENERIC_VNF);
279
280         Collection<AAITreeNode> nodes = ImmutableList.of(
281             nodeMissingData.by(1), nodeMissingData.by(77),
282             nodeMissingData.by(3), nodeMissingData.by(99),
283             nodeWithDataAlready, nodeNotVfModule
284         );
285
286         ///////////// TEST
287
288         aaiTreeNodesEnricher.enrichVfModulesWithModelCustomizationNameFromOtherVersions(nodes, modelInvariantId);
289
290         assertThat(nodes, jsonEquals(ImmutableList.of(
291             nodeWithData.by(1),
292             nodeWithData.by(3),
293             nodeMissingData.by(77), // not in sdcService
294             nodeMissingData.by(99), // not in aaiClient
295             nodeWithDataAlready, // pristine
296             nodeNotVfModule // pristine
297         )).when(Option.IGNORING_ARRAY_ORDER));
298     }
299
300
301     @NotNull
302     private String[] toStringsArray(List<AAITreeNode> nodes) {
303         return toStrings(nodes).toArray(new String[] {});
304     }
305
306     @NotNull
307     private List<String> toStrings(List<AAITreeNode> nodes) {
308         return nodes.stream().map(n -> {
309             final ReflectionToStringBuilder reflectionToStringBuilder = new ReflectionToStringBuilder(n, ToStringStyle.SHORT_PREFIX_STYLE);
310             reflectionToStringBuilder.setExcludeNullValues(true);
311             return reflectionToStringBuilder.toString();
312         }).collect(toList());
313     }
314
315     @NotNull
316     private List<AAITreeNode> nodesWithVersionIdsAndCustomizationNames(List<String> versionIds, List<Names> customizationNames) {
317         return Streams
318                 .zip(versionIds.stream(), customizationNames.stream(), this::nodeWithVersionIdAndCustomizationName)
319                 .collect(toList());
320     }
321
322     @NotNull
323     private List<AAITreeNode> nodesWithVersionIds(List<String> versionIds) {
324         return versionIds.stream()
325                 .map(versionId -> nodeWithVersionIdAndCustomizationName(versionId, new Names(nullString, nullString)))
326                 .collect(toList());
327     }
328
329     private AAITreeNode nodeWithVersionIdAndCustomizationName(String versionId, Names names) {
330         AAITreeNode newNode = new AAITreeNode();
331         newNode.setModelVersionId(versionId.equals(nullString) ? null : versionId);
332         newNode.setModelCustomizationName(names.getModelCustomizationName().equals(nullString) ? null : names.getModelCustomizationName());
333         newNode.setKeyInModel(names.getModelKey().equals(nullString) ? null : names.getModelKey());
334         return newNode;
335     }
336
337 }