Merge "Uplift spring boot version to 3.1.4"
[nonrtric/plt/rappmanager.git] / rapp-manager-dme / src / test / java / com / oransc / rappmanager / dme / service / DmeDeployerTest.java
1 /*-
2  * ============LICENSE_START======================================================================
3  * Copyright (C) 2023 Nordix Foundation. All rights reserved.
4  * ===============================================================================================
5  * Licensed under the Apache License, Version 2.0 (the "License");
6  * you may not use this file except in compliance with the License.
7  * You may obtain a copy of the License at
8  *
9  *      http://www.apache.org/licenses/LICENSE-2.0
10  *
11  * Unless required by applicable law or agreed to in writing, software
12  * distributed under the License is distributed on an "AS IS" BASIS,
13  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14  * See the License for the specific language governing permissions and
15  * limitations under the License.
16  * ============LICENSE_END========================================================================
17  */
18
19 package com.oransc.rappmanager.dme.service;
20
21 import static org.junit.jupiter.api.Assertions.assertEquals;
22 import static org.junit.jupiter.api.Assertions.assertFalse;
23 import static org.junit.jupiter.api.Assertions.assertNull;
24 import static org.junit.jupiter.api.Assertions.assertTrue;
25 import static org.springframework.test.web.client.match.MockRestRequestMatchers.method;
26 import static org.springframework.test.web.client.match.MockRestRequestMatchers.requestTo;
27 import static org.springframework.test.web.client.response.MockRestResponseCreators.withStatus;
28
29 import com.fasterxml.jackson.core.JsonProcessingException;
30 import com.fasterxml.jackson.databind.ObjectMapper;
31 import com.oransc.rappmanager.dme.configuration.DmeConfiguration;
32 import com.oransc.rappmanager.models.cache.RappCacheService;
33 import com.oransc.rappmanager.models.csar.RappCsarConfigurationHandler;
34 import com.oransc.rappmanager.models.rapp.Rapp;
35 import com.oransc.rappmanager.models.rapp.RappDmeResourceBuilder;
36 import com.oransc.rappmanager.models.rapp.RappResources;
37 import com.oransc.rappmanager.models.rapp.RappState;
38 import com.oransc.rappmanager.models.rappinstance.RappInstance;
39 import com.oransc.rappmanager.models.statemachine.RappInstanceStateMachine;
40 import com.oransc.rappmanager.models.statemachine.RappInstanceStateMachineConfig;
41 import java.util.HashSet;
42 import java.util.List;
43 import java.util.Optional;
44 import java.util.Set;
45 import java.util.UUID;
46 import java.util.stream.Stream;
47 import org.junit.jupiter.api.BeforeAll;
48 import org.junit.jupiter.api.BeforeEach;
49 import org.junit.jupiter.api.Test;
50 import org.junit.jupiter.api.TestInstance;
51 import org.junit.jupiter.params.ParameterizedTest;
52 import org.junit.jupiter.params.provider.Arguments;
53 import org.junit.jupiter.params.provider.MethodSource;
54 import org.springframework.beans.factory.annotation.Autowired;
55 import org.springframework.boot.test.autoconfigure.web.servlet.AutoConfigureMockMvc;
56 import org.springframework.boot.test.context.SpringBootTest;
57 import org.springframework.boot.test.mock.mockito.SpyBean;
58 import org.springframework.http.HttpMethod;
59 import org.springframework.http.HttpStatus;
60 import org.springframework.http.MediaType;
61 import org.springframework.test.web.client.ExpectedCount;
62 import org.springframework.test.web.client.MockRestServiceServer;
63 import org.springframework.web.client.RestTemplate;
64
65 @SpringBootTest(classes = {DmeConfiguration.class, DmeDeployer.class, BeanTestConfiguration.class,
66         RappCsarConfigurationHandler.class, RappCacheService.class, RappInstanceStateMachineConfig.class,
67         RappInstanceStateMachine.class})
68 @TestInstance(TestInstance.Lifecycle.PER_CLASS)
69 @AutoConfigureMockMvc
70 class DmeDeployerTest {
71
72     MockRestServiceServer mockServer;
73     @SpyBean
74     DmeDeployer dmeDeployer;
75     @Autowired
76     RestTemplate restTemplate;
77     @Autowired
78     DmeConfiguration dmeConfiguration;
79     @SpyBean
80     RappInstanceStateMachine rappInstanceStateMachine;
81
82     RappDmeResourceBuilder rappDmeResourceBuilder = new RappDmeResourceBuilder();
83
84     private static final String validRappFile = "valid-rapp-package.csar";
85     private static final String validRappFileNewInfoType = "valid-rapp-package-new-info-type.csar";
86     String validCsarFileLocation = "src/test/resources/";
87     ObjectMapper objectMapper = new ObjectMapper();
88
89     String URI_INFO_TYPES, URI_INFO_TYPE, URI_INFO_PRODUCER, URI_INFO_CONSUMER;
90
91     @BeforeAll
92     void initACMURI() {
93         URI_INFO_TYPES = dmeConfiguration.getBaseUrl() + "/data-producer/v1/info-types";
94         URI_INFO_TYPE = dmeConfiguration.getBaseUrl() + "/data-producer/v1/info-types/%s";
95         URI_INFO_PRODUCER = dmeConfiguration.getBaseUrl() + "/data-producer/v1/info-producers/%s";
96         URI_INFO_CONSUMER = dmeConfiguration.getBaseUrl() + "/data-consumer/v1/info-jobs/%s";
97     }
98
99     @BeforeEach
100     public void init() {
101         mockServer = MockRestServiceServer.createServer(restTemplate);
102     }
103
104     @ParameterizedTest
105     @MethodSource("getSuccessParamsWithUnavailableInfoTypes")
106     void testPrimeRappSuccessWithUnavailableInfoType(String rappFile, boolean result) throws JsonProcessingException {
107         RappResources rappResources = rappDmeResourceBuilder.getResources();
108         Rapp rapp = getRapp(Optional.empty());
109         rapp.setPackageName(rappFile);
110         rapp.setRappResources(rappResources);
111         List<String> infoTypes = List.of();
112         mockServer.expect(ExpectedCount.once(), requestTo(URI_INFO_TYPES)).andExpect(method(HttpMethod.GET)).andRespond(
113                 withStatus(HttpStatus.OK).contentType(MediaType.APPLICATION_JSON)
114                         .body(objectMapper.writeValueAsString(infoTypes)));
115         assertTrue(dmeDeployer.primeRapp(rapp));
116         if (rappFile.equals(validRappFileNewInfoType)) {
117             mockServer.verify();
118         }
119         assertEquals(rapp.getIsDmeValid(), result);
120     }
121
122     private static Stream<Arguments> getSuccessParamsWithUnavailableInfoTypes() {
123         return Stream.of(Arguments.of(validRappFile, true), Arguments.of(validRappFileNewInfoType, false));
124     }
125
126     @ParameterizedTest
127     @MethodSource("getSuccessParamsWithAvailableInfoTypes")
128     void testPrimeRappSuccessWithValidInfoType(String rappFile, boolean result) throws JsonProcessingException {
129         RappResources rappResources = rappDmeResourceBuilder.getResources();
130         Rapp rapp = getRapp(Optional.empty());
131         rapp.setPackageName(rappFile);
132         rapp.setRappResources(rappResources);
133         List<String> infoTypes = List.of("new-info-type-not-available");
134         mockServer.expect(ExpectedCount.once(), requestTo(URI_INFO_TYPES)).andExpect(method(HttpMethod.GET)).andRespond(
135                 withStatus(HttpStatus.OK).contentType(MediaType.APPLICATION_JSON)
136                         .body(objectMapper.writeValueAsString(infoTypes)));
137         assertTrue(dmeDeployer.primeRapp(rapp));
138         if (rappFile.equals(validRappFileNewInfoType)) {
139             mockServer.verify();
140         }
141         assertEquals(rapp.getIsDmeValid(), result);
142     }
143
144     private static Stream<Arguments> getSuccessParamsWithAvailableInfoTypes() {
145         return Stream.of(Arguments.of(validRappFile, true), Arguments.of(validRappFileNewInfoType, true));
146     }
147
148     @Test
149     void testPrimeRappFailure() {
150         RappResources rappResources = rappDmeResourceBuilder.getResources();
151         RappResources.DMEResources dme = rappResources.getDme();
152         Set<String> infoProducers = new HashSet<>(rappResources.getDme().getInfoProducers());
153         infoProducers.add("invalid-producer-not-available-in-rapp");
154         dme.setInfoProducers(infoProducers);
155         rappResources.setDme(dme);
156         Rapp rapp = getRapp(Optional.empty());
157         rapp.setRappResources(rappResources);
158         assertFalse(dmeDeployer.primeRapp(rapp));
159         assertFalse(rapp.getIsDmeValid());
160     }
161
162     @Test
163     void testDeprimeRapp() {
164         Rapp rapp = getRapp(Optional.empty());
165         rapp.setIsDmeValid(true);
166         assertTrue(dmeDeployer.deprimeRapp(rapp));
167         assertNull(rapp.getIsDmeValid());
168     }
169
170     @Test
171     void testDeployrAppInstanceSuccess() {
172         Rapp rapp = getRapp(Optional.empty());
173         RappInstance rappInstance = rappDmeResourceBuilder.getRappInstance();
174         getMockServerClientCreateInfoType(rappInstance.getDme().getInfoTypesProducer().toArray()[0].toString(), true);
175         getMockServerClientCreateInfoProducer(rappInstance.getDme().getInfoProducer(), true);
176         getMockServerClientCreateInfoConsumer(rappInstance.getDme().getInfoConsumer(), true);
177         rappInstanceStateMachine.onboardRappInstance(rappInstance.getRappInstanceId());
178         assertTrue(dmeDeployer.deployRappInstance(rapp, rappInstance));
179         mockServer.verify();
180     }
181
182     @Test
183     void testDeployrAppInstanceSuccessWithoutConsumer() {
184         Rapp rapp = getRapp(Optional.empty());
185         RappInstance rappInstance = rappDmeResourceBuilder.getRappInstance();
186         rappInstance.getDme().setInfoTypeConsumer(null);
187         rappInstance.getDme().setInfoConsumer(null);
188         getMockServerClientCreateInfoType(rappInstance.getDme().getInfoTypesProducer().toArray()[0].toString(), true);
189         getMockServerClientCreateInfoProducer(rappInstance.getDme().getInfoProducer(), true);
190         rappInstanceStateMachine.onboardRappInstance(rappInstance.getRappInstanceId());
191         assertTrue(dmeDeployer.deployRappInstance(rapp, rappInstance));
192         mockServer.verify();
193     }
194
195     @Test
196     void testDeployrAppInstanceWithoutProducer() {
197         Rapp rapp = getRapp(Optional.empty());
198         RappInstance rappInstance = rappDmeResourceBuilder.getRappInstance();
199         rappInstance.getDme().setInfoTypesProducer(null);
200         rappInstance.getDme().setInfoProducer(null);
201         getMockServerClientCreateInfoType(rappInstance.getDme().getInfoTypeConsumer(), true);
202         getMockServerClientCreateInfoConsumer(rappInstance.getDme().getInfoConsumer(), true);
203         rappInstanceStateMachine.onboardRappInstance(rappInstance.getRappInstanceId());
204         assertTrue(dmeDeployer.deployRappInstance(rapp, rappInstance));
205         mockServer.verify();
206     }
207
208     @Test
209     void testDeployrAppInstanceFailureWithInfoType() {
210         Rapp rapp = getRapp(Optional.empty());
211         RappInstance rappInstance = rappDmeResourceBuilder.getRappInstance();
212         getMockServerClientCreateInfoType(rappInstance.getDme().getInfoTypesProducer().toArray()[0].toString(), false);
213         rappInstanceStateMachine.onboardRappInstance(rappInstance.getRappInstanceId());
214         assertFalse(dmeDeployer.deployRappInstance(rapp, rappInstance));
215         mockServer.verify();
216     }
217
218     @Test
219     void testDeployrAppInstanceFailureWithInfoProducer() {
220         Rapp rapp = getRapp(Optional.empty());
221         RappInstance rappInstance = rappDmeResourceBuilder.getRappInstance();
222         getMockServerClientCreateInfoType(rappInstance.getDme().getInfoTypesProducer().toArray()[0].toString(), true);
223         getMockServerClientCreateInfoProducer(rappInstance.getDme().getInfoProducer(), false);
224         rappInstanceStateMachine.onboardRappInstance(rappInstance.getRappInstanceId());
225         assertFalse(dmeDeployer.deployRappInstance(rapp, rappInstance));
226         mockServer.verify();
227     }
228
229     @Test
230     void testDeployrAppInstanceFailureWithInfoConsumer() {
231         Rapp rapp = getRapp(Optional.empty());
232         RappInstance rappInstance = rappDmeResourceBuilder.getRappInstance();
233         getMockServerClientCreateInfoType(rappInstance.getDme().getInfoTypesProducer().toArray()[0].toString(), true);
234         getMockServerClientCreateInfoProducer(rappInstance.getDme().getInfoProducer(), true);
235         getMockServerClientCreateInfoConsumer(rappInstance.getDme().getInfoConsumer(), false);
236         rappInstanceStateMachine.onboardRappInstance(rappInstance.getRappInstanceId());
237         assertFalse(dmeDeployer.deployRappInstance(rapp, rappInstance));
238         mockServer.verify();
239     }
240
241     @Test
242     void testUndeployrAppInstanceSuccess() {
243         Rapp rapp = getRapp(Optional.empty());
244         rapp.setState(RappState.PRIMED);
245         RappInstance rappInstance = rappDmeResourceBuilder.getRappInstance();
246         getMockServerClientDeleteInfoConsumer(rappInstance.getDme().getInfoConsumer(), true);
247         getMockServerClientDeleteInfoProducer(rappInstance.getDme().getInfoProducer(), true);
248         rappInstanceStateMachine.onboardRappInstance(rappInstance.getRappInstanceId());
249         assertTrue(dmeDeployer.undeployRappInstance(rapp, rappInstance));
250         mockServer.verify();
251     }
252
253
254     @Test
255     void testUndeployrAppInstanceFailureWithInfoProducer() {
256         Rapp rapp = getRapp(Optional.empty());
257         rapp.setState(RappState.PRIMED);
258         RappInstance rappInstance = rappDmeResourceBuilder.getRappInstance();
259         getMockServerClientDeleteInfoConsumer(rappInstance.getDme().getInfoConsumer(), true);
260         getMockServerClientDeleteInfoProducer(rappInstance.getDme().getInfoProducer(), false);
261         rappInstanceStateMachine.onboardRappInstance(rappInstance.getRappInstanceId());
262         assertFalse(dmeDeployer.undeployRappInstance(rapp, rappInstance));
263         mockServer.verify();
264     }
265
266     @Test
267     void testUndeployrAppInstanceFailureWithInfoConsumer() {
268         Rapp rapp = getRapp(Optional.empty());
269         rapp.setState(RappState.PRIMED);
270         RappInstance rappInstance = rappDmeResourceBuilder.getRappInstance();
271         getMockServerClientDeleteInfoConsumer(rappInstance.getDme().getInfoConsumer(), false);
272         rappInstanceStateMachine.onboardRappInstance(rappInstance.getRappInstanceId());
273         assertFalse(dmeDeployer.undeployRappInstance(rapp, rappInstance));
274         mockServer.verify();
275     }
276
277     @Test
278     void testCreateInfoTypeFailureInvalidInfoType() {
279         Rapp rapp = getRapp(Optional.empty());
280         assertFalse(dmeDeployer.createInfoTypes(rapp, null));
281     }
282
283     @Test
284     void testCreateInfoTypeFailureInvalidInfoProducer() {
285         Rapp rapp = getRapp(Optional.empty());
286         assertFalse(dmeDeployer.createInfoProducer(rapp, ""));
287     }
288
289     @Test
290     void testCreateInfoTypeFailureInvalidInfoConsumer() {
291         Rapp rapp = getRapp(Optional.empty());
292         assertFalse(dmeDeployer.createInfoConsumer(rapp, ""));
293     }
294
295     Rapp getRapp(Optional<UUID> rappOptional) {
296         return Rapp.builder().rappId(rappOptional.orElse(UUID.randomUUID())).name("").packageName(validRappFile)
297                        .packageLocation(validCsarFileLocation).state(RappState.COMMISSIONED).build();
298     }
299
300     void getMockServerClientCreateInfoType(String infoType, boolean isSuccess) {
301         if (isSuccess) {
302             mockServer.expect(ExpectedCount.once(), requestTo(String.format(URI_INFO_TYPE, infoType)))
303                     .andExpect(method(HttpMethod.PUT)).andRespond(withStatus(HttpStatus.CREATED));
304         } else {
305             mockServer.expect(ExpectedCount.once(), requestTo(String.format(URI_INFO_TYPE, infoType)))
306                     .andExpect(method(HttpMethod.PUT)).andRespond(withStatus(HttpStatus.BAD_GATEWAY));
307         }
308     }
309
310     void getMockServerClientCreateInfoProducer(String infoProducer, boolean isSuccess) {
311         if (isSuccess) {
312             mockServer.expect(ExpectedCount.once(), requestTo(String.format(URI_INFO_PRODUCER, infoProducer)))
313                     .andExpect(method(HttpMethod.PUT)).andRespond(withStatus(HttpStatus.CREATED));
314         } else {
315             mockServer.expect(ExpectedCount.once(), requestTo(String.format(URI_INFO_PRODUCER, infoProducer)))
316                     .andExpect(method(HttpMethod.PUT)).andRespond(withStatus(HttpStatus.BAD_GATEWAY));
317         }
318     }
319
320     void getMockServerClientCreateInfoConsumer(String infoConsumer, boolean isSuccess) {
321         if (isSuccess) {
322             mockServer.expect(ExpectedCount.once(), requestTo(String.format(URI_INFO_CONSUMER, infoConsumer)))
323                     .andExpect(method(HttpMethod.PUT)).andRespond(withStatus(HttpStatus.CREATED));
324         } else {
325             mockServer.expect(ExpectedCount.once(), requestTo(String.format(URI_INFO_CONSUMER, infoConsumer)))
326                     .andExpect(method(HttpMethod.PUT)).andRespond(withStatus(HttpStatus.BAD_GATEWAY));
327         }
328     }
329
330     void getMockServerClientDeleteInfoProducer(String infoProducer, boolean isSuccess) {
331         if (isSuccess) {
332             mockServer.expect(ExpectedCount.once(), requestTo(String.format(URI_INFO_PRODUCER, infoProducer)))
333                     .andExpect(method(HttpMethod.DELETE)).andRespond(withStatus(HttpStatus.NO_CONTENT));
334         } else {
335             mockServer.expect(ExpectedCount.once(), requestTo(String.format(URI_INFO_PRODUCER, infoProducer)))
336                     .andExpect(method(HttpMethod.DELETE)).andRespond(withStatus(HttpStatus.BAD_GATEWAY));
337         }
338     }
339
340     void getMockServerClientDeleteInfoConsumer(String infoConsumer, boolean isSuccess) {
341         if (isSuccess) {
342             mockServer.expect(ExpectedCount.once(), requestTo(String.format(URI_INFO_CONSUMER, infoConsumer)))
343                     .andExpect(method(HttpMethod.DELETE)).andRespond(withStatus(HttpStatus.NO_CONTENT));
344         } else {
345             mockServer.expect(ExpectedCount.once(), requestTo(String.format(URI_INFO_CONSUMER, infoConsumer)))
346                     .andExpect(method(HttpMethod.DELETE)).andRespond(withStatus(HttpStatus.BAD_GATEWAY));
347         }
348     }
349
350 }