8c0b99462a1ed71ae9b5cccd658de2fe618b54aa
[policy/drools-applications.git] /
1 /*-
2  * ============LICENSE_START=======================================================
3  * demo
4  * ================================================================================
5  * Copyright (C) 2017 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.policy.template.demo;
22
23 import static org.junit.Assert.assertEquals;
24 import static org.junit.Assert.assertFalse;
25 import static org.junit.Assert.assertNotNull;
26 import static org.junit.Assert.assertTrue;
27 import static org.junit.Assert.fail;
28
29 import java.io.IOException;
30 import java.net.URLEncoder;
31 import java.time.Instant;
32 import java.util.HashMap;
33 import java.util.UUID;
34
35 import org.junit.AfterClass;
36 import org.junit.BeforeClass;
37 import org.junit.Ignore;
38 import org.junit.Test;
39 import org.kie.api.runtime.KieSession;
40 import org.kie.api.runtime.rule.FactHandle;
41 import org.onap.policy.appclcm.LCMRequest;
42 import org.onap.policy.appclcm.LCMRequestWrapper;
43 import org.onap.policy.appclcm.LCMResponse;
44 import org.onap.policy.appclcm.LCMResponseWrapper;
45 import org.onap.policy.controlloop.ControlLoopEventStatus;
46 import org.onap.policy.controlloop.ControlLoopNotificationType;
47
48 import org.onap.policy.controlloop.VirtualControlLoopEvent;
49 import org.onap.policy.controlloop.VirtualControlLoopNotification;
50 import org.onap.policy.controlloop.policy.ControlLoopPolicy;
51 import org.onap.policy.controlloop.policy.TargetType;
52 import org.onap.policy.drools.http.server.HttpServletServer;
53 import org.onap.policy.drools.impl.PolicyEngineJUnitImpl;
54 import org.onap.policy.guard.PolicyGuard;
55 import org.slf4j.Logger;
56 import org.slf4j.LoggerFactory;
57 //import org.onap.policy.controlloop.policy.guard.ControlLoopGuard;
58
59
60 public class ControlLoopXacmlGuardTest {
61     @BeforeClass
62     public static void setUpSimulator() {
63         try {
64             Util.buildAaiSim();
65         } catch (InterruptedException e) {
66             fail(e.getMessage());
67         }
68     }
69     
70     @AfterClass
71     public static void tearDownSimulator() {
72         HttpServletServer.factory.destroy();
73     }
74     
75         private static final Logger logger = LoggerFactory.getLogger(ControlLoopXacmlGuardTest.class);
76
77         @Test
78         public void test() {
79                 try {
80                         this.runTest("src/main/resources/ControlLoop_Template_xacml_guard.drl", 
81                                         "src/test/resources/yaml/policy_ControlLoop_Service123.yaml",
82                                         "service=Service123;resource=Res123;type=operational", 
83                                         "CL_SERV123_8888", 
84                                         "org.onap.closed_loop.Service123:VNFS:0.0.1");
85                 } catch (IOException e) {
86                         e.printStackTrace();
87                         fail(e.getMessage());
88                 }
89         }
90         
91         public void runTest(String droolsTemplate, 
92                         String yamlFile, 
93                         String policyScope, 
94                         String policyName, 
95                         String policyVersion) throws IOException {
96                 //
97                 // Pull info from the yaml
98                 //
99                 final Util.Pair<ControlLoopPolicy, String> pair = Util.loadYaml(yamlFile);
100                 assertNotNull(pair);
101                 assertNotNull(pair.a);
102                 assertNotNull(pair.a.getControlLoop());
103                 assertNotNull(pair.a.getControlLoop().getControlLoopName());
104                 assertTrue(pair.a.getControlLoop().getControlLoopName().length() > 0);
105                 //
106                 // Build a container
107                 //
108                 final KieSession kieSession = Util.buildContainer(droolsTemplate, 
109                                 pair.a.getControlLoop().getControlLoopName(), 
110                                 policyScope, 
111                                 policyName, 
112                                 policyVersion, 
113                                 URLEncoder.encode(pair.b, "UTF-8"));
114                 
115                 
116                 logger.debug("============");
117                 logger.debug(URLEncoder.encode(pair.b, "UTF-8"));
118                 logger.debug("============");
119                 
120                 final PolicyEngineJUnitImpl engine = (PolicyEngineJUnitImpl) kieSession.getGlobal("Engine");
121                 
122                 //
123                 // Initial fire of rules
124                 //
125                 kieSession.fireAllRules();
126                 //
127                 // Kick a thread that starts testing
128                 //
129                 new Thread(new Runnable() {
130
131
132                         @Override
133                         public void run() {
134                                 try {
135                                         
136                                                 
137                                         //
138                                         // Let's use a unique ID for the request and
139                                         // a unique trigger source.
140                                         //
141                                         UUID requestID = UUID.randomUUID();
142                                         String triggerSourceName = "foobartriggersource36";
143                                         
144                                         Object obj = null;
145                                         
146                                         sendGoodEvents(kieSession, pair.a, requestID, triggerSourceName);
147                                         obj = engine.subscribe("UEB", "POLICY-CL-MGT");
148                                         assertNotNull(obj);
149                                         assertTrue(obj instanceof VirtualControlLoopNotification);
150                                         assertTrue(((VirtualControlLoopNotification)obj).notification.equals(ControlLoopNotificationType.ACTIVE));
151                                         //
152                                         // Give the control loop a little time to acquire the lock and publish the request
153                                         //
154                                         Thread.sleep(2000);
155                                         
156                                         
157                                         // "About to query Guard" notification (Querying about Restart)
158                                         obj = engine.subscribe("UEB", "POLICY-CL-MGT");
159                                         assertNotNull(obj);
160                                         logger.debug("\n\n####################### GOING TO QUERY GUARD about Restart!!!!!!");
161                                         logger.debug("Rule: {} Message {}", ((VirtualControlLoopNotification)obj).policyName, ((VirtualControlLoopNotification)obj).message);
162                                         assertTrue(obj instanceof VirtualControlLoopNotification);
163                                         assertTrue(((VirtualControlLoopNotification)obj).notification.equals(ControlLoopNotificationType.OPERATION));
164                                 
165                                         Thread.sleep(2000);
166                                         // "Response from Guard" notification
167                                         obj = engine.subscribe("UEB", "POLICY-CL-MGT");
168                                         assertNotNull(obj);
169                                         logger.debug("Rule: {} Message {}", ((VirtualControlLoopNotification)obj).policyName, ((VirtualControlLoopNotification)obj).message);
170                                         assertTrue(obj instanceof VirtualControlLoopNotification);
171                                         assertTrue(((VirtualControlLoopNotification)obj).notification.equals(ControlLoopNotificationType.OPERATION));
172                                 
173                                         
174                                         if(true == ((VirtualControlLoopNotification)obj).message.contains("Guard result: Deny")){
175                                                 
176                                                 // "About to query Guard" notification (Querying about Rebuild)
177                                                 obj = engine.subscribe("UEB", "POLICY-CL-MGT");
178                                                 assertNotNull(obj);
179                                                 logger.debug("\n\n####################### GOING TO QUERY GUARD about Rebuild!!!!!!");
180                                                 logger.debug("Rule: {} Message", ((VirtualControlLoopNotification)obj).policyName, ((VirtualControlLoopNotification)obj).message);
181                                                 assertTrue(obj instanceof VirtualControlLoopNotification);
182                                                 assertTrue(((VirtualControlLoopNotification)obj).notification.equals(ControlLoopNotificationType.OPERATION));
183                                         
184                                                 Thread.sleep(2000);
185                                                 
186                                                 // "Response from Guard" notification
187                                                 obj = engine.subscribe("UEB", "POLICY-CL-MGT");
188                                                 assertNotNull(obj);
189                                                 logger.debug("Rule: {} Message {}", ((VirtualControlLoopNotification)obj).policyName, ((VirtualControlLoopNotification)obj).message);
190                                                 assertTrue(obj instanceof VirtualControlLoopNotification);
191                                                 assertTrue(((VirtualControlLoopNotification)obj).notification.equals(ControlLoopNotificationType.OPERATION));
192                                                 
193                                                 
194                                                 if(true == ((VirtualControlLoopNotification)obj).message.contains("Guard result: Deny")){
195                                                         
196                                                         // "About to query Guard" notification (Querying about Migrate)
197                                                         obj = engine.subscribe("UEB", "POLICY-CL-MGT");
198                                                         assertNotNull(obj);
199                                                         logger.debug("\n\n####################### GOING TO QUERY GUARD!!!!!!");
200                                                         logger.debug("Rule: {} Message {}", ((VirtualControlLoopNotification)obj).policyName, ((VirtualControlLoopNotification)obj).message);
201                                                         assertTrue(obj instanceof VirtualControlLoopNotification);
202                                                         assertTrue(((VirtualControlLoopNotification)obj).notification.equals(ControlLoopNotificationType.OPERATION));
203                                                         
204                                                         Thread.sleep(2000);
205                                                         
206                                                         // "Response from Guard" notification
207                                                         obj = engine.subscribe("UEB", "POLICY-CL-MGT");
208                                                         assertNotNull(obj);
209                                                         logger.debug("Rule: " + ((VirtualControlLoopNotification)obj).policyName +" Message: " + ((VirtualControlLoopNotification)obj).message);
210                                                         assertTrue(obj instanceof VirtualControlLoopNotification);
211                                                         assertTrue(((VirtualControlLoopNotification)obj).notification.equals(ControlLoopNotificationType.OPERATION));
212                                                         
213                                                         
214                                                         if(true == ((VirtualControlLoopNotification)obj).message.contains("Guard result: Deny")){
215                                                                 //All the 3 operations were Denied by Guard
216                                                                 Thread.sleep(30000);
217                                                                 
218                                                         }       
219                                                 }
220                                         }
221                                         
222                                         //
223                                         // In case one of the operations was permitted by Guard
224                                         //
225                                         if(true == ((VirtualControlLoopNotification)obj).message.contains("Guard result: Permit")){
226                                                 obj = engine.subscribe("UEB", "POLICY-CL-MGT");
227                                                 assertNotNull(obj);
228                                                 logger.debug("Rule: {} Message {}", ((VirtualControlLoopNotification)obj).policyName, ((VirtualControlLoopNotification)obj).message);
229                                                 assertTrue(obj instanceof VirtualControlLoopNotification);
230                                                 assertTrue(((VirtualControlLoopNotification)obj).notification.equals(ControlLoopNotificationType.OPERATION));
231                                                 
232                                                 Thread.sleep(500);
233                                                 
234                                                 obj = engine.subscribe("UEB", "APPC-CL");
235                                                 assertNotNull(obj);
236                                                 assertTrue(obj instanceof LCMRequestWrapper);
237                                                 LCMRequestWrapper dmaapRequest = (LCMRequestWrapper) obj;
238                                                 LCMRequest appcRequest = dmaapRequest.getBody();
239                                                 assertTrue(appcRequest.getCommonHeader().getSubRequestId().equals("1"));
240                                                 
241                                                 logger.debug("\n============ APP-C Got request!!! ===========\n");
242                                                 //
243                                                 // Ok - let's simulate ACCEPT
244                                                 //
245
246                                                 //
247                                                 // now wait for it to finish
248                                                 //
249                                                 Thread.sleep(500);
250                                                 
251                                                 //
252                                                 // Now we are going to success it
253                                                 //
254                                                 LCMResponseWrapper dmaapResponse = new LCMResponseWrapper();
255                                                 LCMResponse appcResponse = new LCMResponse(appcRequest);
256                                                 appcResponse.getStatus().setCode(400);
257                                                 appcResponse.getStatus().setMessage("AppC success");
258                                                 dmaapResponse.setBody(appcResponse);
259                                                 kieSession.insert(dmaapResponse);
260                                                 //
261                                                 // Give it some time to process
262                                                 //
263                                                 Thread.sleep(2000);
264                                                 //
265                                                 // Insert the abatement event
266                                                 //
267                                                 sendAbatement(kieSession, pair.a, requestID, triggerSourceName);
268                                                 //
269                                                 // now wait for it to finish
270                                                 //
271                                                 Thread.sleep(15000);                            
272                                                 //
273                                                 // Ensure they released the lock
274                                                 //
275                                                 assertFalse(PolicyGuard.isLocked(TargetType.VM, triggerSourceName, requestID));
276                                                 
277                                         }
278                                         
279                                         
280                                         
281                                 } catch (InterruptedException e) {
282                                         logger.error("Test thread got InterruptedException ", e.getLocalizedMessage());
283                                 } catch (AssertionError e) {
284                                         logger.error("Test thread got AssertionError ", e.getLocalizedMessage());
285                                         e.printStackTrace();
286                                 } catch (Exception e) {
287                                         logger.error("Test thread got Exception ", e.getLocalizedMessage());
288                                         e.printStackTrace();
289                                 }
290                                 kieSession.halt();
291                         }
292                         
293                 }).start();
294                 //
295                 // Start firing rules
296                 //
297                 kieSession.fireUntilHalt();
298                 //
299                 // Dump working memory
300                 //
301                 dumpFacts(kieSession);
302                 //
303                 // See if there is anything left in memory
304                 //
305                 assertEquals(1, kieSession.getFactCount());
306                 
307                 for (FactHandle handle : kieSession.getFactHandles()) {
308                         Object fact = kieSession.getObject(handle);
309                         assertEquals("", "org.onap.policy.controlloop.Params", fact.getClass().getName());
310                 }
311                 kieSession.dispose();
312         }
313         
314
315         
316         
317         public static void dumpFacts(KieSession kieSession) {
318                 logger.debug("Fact Count: {}", kieSession.getFactCount());
319                 for (FactHandle handle : kieSession.getFactHandles()) {
320                         logger.debug("FACT: {}", handle);
321                 }
322         }
323
324         protected void sendAbatement(KieSession kieSession, ControlLoopPolicy policy, UUID requestID, String triggerSourceName) throws InterruptedException {
325                 VirtualControlLoopEvent event = new VirtualControlLoopEvent();
326                 event.closedLoopControlName = policy.getControlLoop().getControlLoopName();
327                 event.requestID = requestID;
328                 event.target = "vserver.vserver-name";
329                 event.closedLoopAlarmStart = Instant.now().minusSeconds(5);
330                 event.closedLoopAlarmEnd = Instant.now();
331                 event.AAI = new HashMap<>();
332                 event.AAI.put("cloud-region.identity-url", "foo");
333                 event.AAI.put("vserver.selflink", "bar");
334                 event.AAI.put("vserver.is-closed-loop-disabled", "false");
335                 event.AAI.put("generic-vnf.vnf-name", "testGenericVnfName");
336                 event.closedLoopEventStatus = ControlLoopEventStatus.ABATED;
337                 kieSession.insert(event);
338         }
339         
340         protected void sendGoodEvents(KieSession kieSession, ControlLoopPolicy policy, UUID requestID, String triggerSourceName) throws InterruptedException {
341                 VirtualControlLoopEvent event = new VirtualControlLoopEvent();
342                 event.closedLoopControlName = policy.getControlLoop().getControlLoopName();
343                 event.requestID = requestID;
344                 event.target = "vserver.vserver-name";
345                 event.closedLoopAlarmStart = Instant.now();
346                 event.AAI = new HashMap<>();
347                 event.AAI.put("cloud-region.identity-url", "foo");
348                 event.AAI.put("vserver.selflink", "bar");
349                 event.AAI.put("vserver.is-closed-loop-disabled", "false");
350                 event.AAI.put("vserver.vserver-name", "testGenericVnfName");
351                 event.closedLoopEventStatus = ControlLoopEventStatus.ONSET;
352                 kieSession.insert(event);
353                 Thread.sleep(1000);
354                 
355         }
356         
357         protected void sendBadEvents(KieSession kieSession, ControlLoopPolicy policy, UUID requestID, String triggerSourceName) throws InterruptedException {
358                 //
359                 // Insert a bad Event
360                 //
361                 VirtualControlLoopEvent event = new VirtualControlLoopEvent();
362                 event.closedLoopControlName = policy.getControlLoop().getControlLoopName();
363                 kieSession.insert(event);
364                 Thread.sleep(250);
365                 //
366                 // add the request id
367                 //
368                 event.requestID = requestID;
369                 kieSession.insert(event);
370                 Thread.sleep(250);
371                 //
372                 // add some aai
373                 //
374                 event.AAI = new HashMap<>();
375                 event.AAI.put("cloud-region.identity-url", "foo");
376                 event.AAI.put("vserver.selflink", "bar");
377                 event.AAI.put("vserver.vserver-name", "vmfoo");
378                 kieSession.insert(event);
379                 Thread.sleep(250);
380                 //
381                 // set a valid status
382                 //
383                 event.closedLoopEventStatus = ControlLoopEventStatus.ONSET;
384                 kieSession.insert(event);
385                 Thread.sleep(250);
386                 //
387                 // add a trigger sourcename
388                 //
389                 kieSession.insert(event);
390                 Thread.sleep(250);
391                 //
392                 // add is closed-loop-disabled
393                 //
394                 event.AAI.put("vserver.is-closed-loop-disabled", "true");
395                 kieSession.insert(event);
396                 Thread.sleep(250);
397                 //
398                 // now enable
399                 //
400                 event.AAI.put("vserver.is-closed-loop-disabled", "false");
401                 kieSession.insert(event);
402                 Thread.sleep(250);
403                 //
404                 // Add target, but bad.
405                 //
406                 event.target = "VM_BLAH";
407                 kieSession.insert(event);
408                 Thread.sleep(250);
409         }
410 }