Add more coverage to drools-pdp health check
[policy/drools-pdp.git] / feature-healthcheck / src / test / java / org / onap / policy / drools / healthcheck / HealthCheckTest.java
1 /*
2  * ============LICENSE_START=======================================================
3  * ONAP
4  * ================================================================================
5  * Copyright (C) 2018 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.drools.healthcheck;
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.mockito.Mockito.mock;
28 import static org.mockito.Mockito.verify;
29 import static org.mockito.Mockito.when;
30
31 import java.net.HttpURLConnection;
32 import java.util.Arrays;
33 import java.util.Collections;
34 import java.util.List;
35 import java.util.Properties;
36 import javax.ws.rs.core.Response;
37 import org.junit.Before;
38 import org.junit.Test;
39 import org.onap.policy.common.endpoints.http.client.HttpClient;
40 import org.onap.policy.common.endpoints.http.client.HttpClientFactory;
41 import org.onap.policy.common.endpoints.http.server.HttpServletServer;
42 import org.onap.policy.common.endpoints.http.server.HttpServletServerFactory;
43 import org.onap.policy.drools.healthcheck.HealthCheck.Report;
44 import org.onap.policy.drools.healthcheck.HealthCheck.Reports;
45 import org.onap.policy.drools.system.PolicyEngine;
46
47 public class HealthCheckTest {
48
49     private static final int RPT_CODE = 100;
50     private static final String RPT_MSG = "report-message";
51     private static final String RPT_NAME = "report-name";
52     private static final String RPT_URL = "report-url";
53     private static final String EXPECTED = "expected exception";
54
55     private static final String CLIENT_NAME1 = "name-a";
56     private static final String CLIENT_URL1 = "url-a";
57     private static final String CLIENT_NAME2 = "name-b";
58     private static final String CLIENT_URL2 = "url-b";
59     private static final String CLIENT_NAME3 = "name-c";
60     private static final String CLIENT_URL3 = "url-c";
61
62     private Properties properties;
63     private HttpServletServerFactory servletFactory;
64     private HttpServletServer server1;
65     private HttpServletServer server2;
66     private HttpClientFactory clientFactory;
67     private HttpClient client1;
68     private HttpClient client2;
69     private HttpClient client3;
70     private List<HttpServletServer> servers;
71     private List<HttpClient> clients;
72     private PolicyEngine engineMgr;
73     private HealthCheckMonitor monitor;
74
75     /**
76      * Initializes the object to be tested.
77      *
78      * @throws Exception if an error occurs
79      */
80     @Before
81     public void setUp() throws Exception {
82         properties = new Properties();
83         servletFactory = mock(HttpServletServerFactory.class);
84         server1 = mock(HttpServletServer.class);
85         server2 = mock(HttpServletServer.class);
86         clientFactory = mock(HttpClientFactory.class);
87         client1 = mock(HttpClient.class);
88         client2 = mock(HttpClient.class);
89         client3 = mock(HttpClient.class);
90         servers = Arrays.asList(server1, server2);
91         clients = Arrays.asList(client1, client2, client3);
92         engineMgr = mock(PolicyEngine.class);
93
94         when(client1.getName()).thenReturn(CLIENT_NAME1);
95         when(client1.getBaseUrl()).thenReturn(CLIENT_URL1);
96         when(client2.getName()).thenReturn(CLIENT_NAME2);
97         when(client2.getBaseUrl()).thenReturn(CLIENT_URL2);
98         when(client3.getName()).thenReturn(CLIENT_NAME3);
99         when(client3.getBaseUrl()).thenReturn(CLIENT_URL3);
100         when(servletFactory.build(properties)).thenReturn(servers);
101         when(clientFactory.build(properties)).thenReturn(clients);
102         when(engineMgr.isAlive()).thenReturn(true);
103
104         monitor = new HealthCheckMonitorImpl();
105     }
106
107     @Test
108     public void testReport() {
109         Report rpt = new Report();
110
111         // toString should work with un-populated data
112         assertNotNull(rpt.toString());
113
114         rpt.setCode(RPT_CODE);
115         rpt.setHealthy(true);
116         rpt.setMessage(RPT_MSG);
117         rpt.setName(RPT_NAME);
118         rpt.setUrl(RPT_URL);
119
120         assertEquals(RPT_CODE, rpt.getCode());
121         assertEquals(true, rpt.isHealthy());
122         assertEquals(RPT_MSG, rpt.getMessage());
123         assertEquals(RPT_NAME, rpt.getName());
124         assertEquals(RPT_URL, rpt.getUrl());
125
126         // flip the flag
127         rpt.setHealthy(false);
128         assertEquals(false, rpt.isHealthy());
129
130         // toString should work with populated data
131         assertNotNull(rpt.toString());
132     }
133
134     @Test
135     public void testReports() {
136         Reports reports = new Reports();
137
138         // toString should work with un-populated data
139         assertNotNull(reports.toString());
140
141         List<Report> lst = Collections.emptyList();
142         reports.setDetails(lst);
143         reports.setHealthy(true);
144
145         assertTrue(lst == reports.getDetails());
146         assertEquals(true, reports.isHealthy());
147
148         // flip the flag
149         reports.setHealthy(false);
150         assertEquals(false, reports.isHealthy());
151
152         // toString should work with populated data
153         assertNotNull(reports.toString());
154     }
155
156     @Test
157     public void testHealthCheckMonitor_HealthCheck() {
158         monitor.start();
159
160         // first client is healthy
161         Response resp = mock(Response.class);
162         when(resp.getStatus()).thenReturn(HttpURLConnection.HTTP_OK);
163         when(resp.readEntity(String.class)).thenReturn(RPT_MSG);
164         when(client1.get()).thenReturn(resp);
165
166         // second client throws an exception
167         when(client2.get()).thenThrow(new RuntimeException(EXPECTED));
168
169         // third client is not healthy
170         resp = mock(Response.class);
171         when(resp.getStatus()).thenReturn(HttpURLConnection.HTTP_INTERNAL_ERROR);
172         when(resp.readEntity(String.class)).thenReturn(RPT_NAME);
173         when(client3.get()).thenReturn(resp);
174
175         Reports reports = monitor.healthCheck();
176         assertNotNull(reports);
177         assertEquals(4, reports.getDetails().size());
178         assertFalse(reports.isHealthy());
179
180         int index = 0;
181
182         Report report = reports.getDetails().get(index++);
183         assertEquals(true, report.isHealthy());
184         assertEquals("PDP-D", report.getName());
185         assertEquals("self", report.getUrl());
186         assertEquals("alive", report.getMessage());
187         assertEquals(HttpURLConnection.HTTP_OK, report.getCode());
188
189         report = reports.getDetails().get(index++);
190         assertEquals(true, report.isHealthy());
191         assertEquals(client1.getName(), report.getName());
192         assertEquals(client1.getBaseUrl(), report.getUrl());
193         assertEquals(RPT_MSG, report.getMessage());
194         assertEquals(HttpURLConnection.HTTP_OK, report.getCode());
195
196         report = reports.getDetails().get(index++);
197         assertEquals(false, report.isHealthy());
198         assertEquals(client2.getName(), report.getName());
199         assertEquals(client2.getBaseUrl(), report.getUrl());
200
201         report = reports.getDetails().get(index++);
202         assertEquals(false, report.isHealthy());
203         assertEquals(client3.getName(), report.getName());
204         assertEquals(client3.getBaseUrl(), report.getUrl());
205         assertEquals(RPT_NAME, report.getMessage());
206         assertEquals(HttpURLConnection.HTTP_INTERNAL_ERROR, report.getCode());
207
208         // indicate that engine is no longer healthy and re-run health check
209         when(engineMgr.isAlive()).thenReturn(false);
210
211         reports = monitor.healthCheck();
212         report = reports.getDetails().get(0);
213
214         assertEquals(false, report.isHealthy());
215         assertEquals("not alive", report.getMessage());
216         assertEquals(500, report.getCode());
217     }
218
219     @Test
220     public void testHealthCheckMonitor_Start() {
221         // arrange for one server to throw an exception
222         when(server1.start()).thenThrow(new RuntimeException(EXPECTED));
223
224         assertTrue(monitor.start());
225
226         verify(server1).start();
227         verify(server2).start();
228
229         /*
230          * Generate exception during building.
231          */
232
233         // new monitor
234         monitor = new HealthCheckMonitorImpl() {
235             @Override
236             protected HttpServletServerFactory getServerFactory() {
237                 throw new RuntimeException(EXPECTED);
238             }
239         };
240
241         assertFalse(monitor.start());
242     }
243
244     @Test
245     public void testHealthCheckMonitor_Stop() {
246         monitor.start();
247
248         // arrange for one server and one client to throw an exception
249         when(server1.stop()).thenThrow(new RuntimeException(EXPECTED));
250         when(client2.stop()).thenThrow(new RuntimeException(EXPECTED));
251
252         assertTrue(monitor.stop());
253
254         verify(server1).stop();
255         verify(server2).stop();
256         verify(client1).stop();
257         verify(client2).stop();
258         verify(client3).stop();
259     }
260
261     @Test
262     public void testHealthCheckMonitor_Shutdown() {
263         monitor.start();
264         monitor.shutdown();
265
266         // at least one "stop" should have been called
267         verify(server1).stop();
268     }
269
270     @Test
271     public void testHealthCheckMonitor_IsAlive() {
272         assertFalse(monitor.isAlive());
273
274         monitor.start();
275         assertTrue(monitor.isAlive());
276     }
277
278     @Test
279     public void testHealthCheckMonitor_GetServers_GetClients() {
280         monitor.start();
281         assertEquals(servers, monitor.getServers());
282         assertEquals(clients, monitor.getClients());
283     }
284
285     @Test
286     public void testHealthCheckMonitor_GetHttpBody() {
287         Response response = mock(Response.class);
288         when(response.readEntity(String.class)).thenReturn(RPT_MSG);
289         assertEquals(RPT_MSG, monitor.getHttpBody(response, client1));
290
291         // readEntity() throws an exception
292         when(response.readEntity(String.class)).thenThrow(new RuntimeException(EXPECTED));
293         assertEquals(null, monitor.getHttpBody(response, client1));
294     }
295
296     @Test
297     public void testHealthCheckMonitor_StartServer() {
298         monitor.startServer(server1);
299         verify(server1).start();
300
301         // force start() to throw an exception - monitor should still work
302         when(server1.start()).thenThrow(new RuntimeException(EXPECTED));
303         monitor.startServer(server1);
304     }
305
306     @Test
307     public void testHealthCheckMonitor_ToString() {
308         assertTrue(monitor.toString().startsWith("HealthCheckMonitor ["));
309     }
310
311     @Test
312     public void testHealthCheckMonitor_GetEngineManager() {
313         assertNotNull(new HealthCheckMonitor().getEngineManager());
314     }
315
316     @Test
317     public void testHealthCheckMonitor_GetServerFactory() {
318         assertNotNull(new HealthCheckMonitor().getServerFactory());
319     }
320
321     @Test
322     public void testHealthCheckMonitor_GetClientFactory() {
323         assertNotNull(new HealthCheckMonitor().getClientFactory());
324     }
325
326     /**
327      * Monitor with overrides.
328      */
329     private class HealthCheckMonitorImpl extends HealthCheckMonitor {
330
331         @Override
332         protected PolicyEngine getEngineManager() {
333             return engineMgr;
334         }
335
336         @Override
337         protected HttpServletServerFactory getServerFactory() {
338             return servletFactory;
339         }
340
341         @Override
342         protected HttpClientFactory getClientFactory() {
343             return clientFactory;
344         }
345
346         @Override
347         protected Properties getPersistentProperties(String propertyName) {
348             return properties;
349         }
350
351     }
352 }