c367d133515411d7147509b5be13b0ab9f63b5d0
[policy/common.git] /
1 /*-
2  * ============LICENSE_START=======================================================
3  * ONAP
4  * ================================================================================
5  * Copyright (C) 2017-2020 AT&T Intellectual Property. All rights reserved.
6  * Modifications Copyright (C) 2020 Nordix Foundation.
7  * ================================================================================
8  * Licensed under the Apache License, Version 2.0 (the "License");
9  * you may not use this file except in compliance with the License.
10  * You may obtain a copy of the License at
11  *
12  *      http://www.apache.org/licenses/LICENSE-2.0
13  *
14  * Unless required by applicable law or agreed to in writing, software
15  * distributed under the License is distributed on an "AS IS" BASIS,
16  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17  * See the License for the specific language governing permissions and
18  * limitations under the License.
19  * ============LICENSE_END=========================================================
20  */
21
22 package org.onap.policy.common.endpoints.http.server.test;
23
24 import static org.assertj.core.api.Assertions.assertThat;
25 import static org.assertj.core.api.Assertions.assertThatCode;
26 import static org.assertj.core.api.Assertions.assertThatThrownBy;
27 import static org.assertj.core.api.Assertions.catchThrowable;
28 import static org.junit.Assert.assertEquals;
29 import static org.junit.Assert.assertFalse;
30 import static org.junit.Assert.assertNotNull;
31 import static org.junit.Assert.assertTrue;
32
33 import com.google.gson.Gson;
34 import java.io.IOException;
35 import java.io.InputStream;
36 import java.net.HttpURLConnection;
37 import java.net.MalformedURLException;
38 import java.net.URL;
39 import java.net.URLConnection;
40 import java.nio.charset.StandardCharsets;
41 import java.util.UUID;
42 import org.apache.commons.io.IOUtils;
43 import org.junit.AfterClass;
44 import org.junit.Before;
45 import org.junit.Test;
46 import org.onap.policy.common.endpoints.http.server.HttpServletServer;
47 import org.onap.policy.common.endpoints.http.server.HttpServletServerFactoryInstance;
48 import org.onap.policy.common.endpoints.http.server.YamlMessageBodyHandler;
49 import org.onap.policy.common.utils.coder.StandardYamlCoder;
50 import org.onap.policy.common.utils.gson.GsonTestUtils;
51 import org.onap.policy.common.utils.network.NetworkUtil;
52 import org.slf4j.Logger;
53 import org.slf4j.LoggerFactory;
54
55 /**
56  * HttpServletServer JUNIT tests.
57  */
58 public class HttpServerTest {
59     private static final String LOCALHOST = "localhost";
60     private static final String JSON_MEDIA = "application/json";
61     private static final String YAML_MEDIA = YamlMessageBodyHandler.APPLICATION_YAML;
62     private static final String SWAGGER_JSON = "/swagger.json";
63     private static final String JUNIT_ECHO_HELLO = "/junit/echo/hello";
64     private static final String JUNIT_ECHO_FULL_REQUEST = "/junit/echo/full/request";
65     private static final String SOME_TEXT = "some text";
66     private static final String HELLO = "hello";
67
68     /**
69      * Logger.
70      */
71     private static Logger logger = LoggerFactory.getLogger(HttpServerTest.class);
72
73     private static final String LOCALHOST_PREFIX = "http://localhost:";
74
75     private static final Gson gson = new Gson();
76
77     /**
78      * Server port.  Incremented by 10 with each test.
79      */
80     private static int port = 5608;
81
82     private String portUrl;
83
84     /**
85      * Increments the port number, clears the servers, and resets the providers.
86      */
87     @Before
88     public void setUp() {
89         incrementPort();
90         portUrl = LOCALHOST_PREFIX + port;
91
92         HttpServletServerFactoryInstance.getServerFactory().destroy();
93
94         MyJacksonProvider.resetSome();
95         MyGsonProvider.resetSome();
96         MyYamlProvider.resetSome();
97     }
98
99     private static void incrementPort() {
100         port += 10;
101     }
102
103     /**
104      * To delete temporary properties cadi_longitude,and cadi_latitude.
105      */
106     @AfterClass
107     public static void tearDownAfterClass() {
108         HttpServletServerFactoryInstance.getServerFactory().destroy();
109         System.clearProperty("cadi_longitude");
110         System.clearProperty("cadi_latitude");
111     }
112
113     @Test
114     public void testDefaultPackageServer() throws Exception {
115         logger.info("-- testDefaultPackageServer() --");
116
117         HttpServletServer server = HttpServletServerFactoryInstance.getServerFactory()
118                         .build("echo", LOCALHOST, port, "/", false, true);
119         server.addServletPackage("/*", this.getClass().getPackage().getName());
120         server.addFilterClass("/*", TestFilter.class.getName());
121         server.waitedStart(5000);
122
123         assertTrue(HttpServletServerFactoryInstance.getServerFactory().get(port).isAlive());
124
125         RestEchoReqResp request = new RestEchoReqResp();
126         request.setRequestId(100);
127         request.setText(SOME_TEXT);
128         String reqText = gson.toJson(request);
129
130         String response = http(portUrl + JUNIT_ECHO_FULL_REQUEST, JSON_MEDIA, reqText);
131         assertEquals(reqText, response);
132     }
133
134     @Test
135     public void testJacksonPackageServer() throws Exception {
136         logger.info("-- testJacksonPackageServer() --");
137
138         HttpServletServer server = HttpServletServerFactoryInstance.getServerFactory()
139                         .build("echo", LOCALHOST, port, "/", false, true);
140
141         server.setSerializationProvider(MyJacksonProvider.class.getName());
142         server.addServletPackage("/*", this.getClass().getPackage().getName());
143         server.addFilterClass("/*", TestFilter.class.getName());
144         server.waitedStart(5000);
145
146         assertTrue(HttpServletServerFactoryInstance.getServerFactory().get(port).isAlive());
147
148         RestEchoReqResp request = new RestEchoReqResp();
149         request.setRequestId(100);
150         request.setText(SOME_TEXT);
151         String reqText = gson.toJson(request);
152
153         String response = http(portUrl + JUNIT_ECHO_FULL_REQUEST, JSON_MEDIA, reqText);
154         assertEquals(reqText, response);
155
156         assertTrue(MyJacksonProvider.hasReadSome());
157         assertTrue(MyJacksonProvider.hasWrittenSome());
158
159         assertFalse(MyGsonProvider.hasReadSome());
160         assertFalse(MyGsonProvider.hasWrittenSome());
161
162         assertFalse(MyYamlProvider.hasReadSome());
163         assertFalse(MyYamlProvider.hasWrittenSome());
164     }
165
166     @Test
167     public void testGsonPackageServer() throws Exception {
168         logger.info("-- testGsonPackageServer() --");
169
170         HttpServletServer server = HttpServletServerFactoryInstance.getServerFactory()
171                         .build("echo", LOCALHOST, port, "/", false, true);
172
173         server.setSerializationProvider(MyGsonProvider.class.getName());
174         server.addServletPackage("/*", this.getClass().getPackage().getName());
175         server.addFilterClass("/*", TestFilter.class.getName());
176         server.waitedStart(5000);
177
178         assertTrue(HttpServletServerFactoryInstance.getServerFactory().get(port).isAlive());
179
180         RestEchoReqResp request = new RestEchoReqResp();
181         request.setRequestId(100);
182         request.setText(SOME_TEXT);
183         String reqText = gson.toJson(request);
184
185         String response = http(portUrl + JUNIT_ECHO_FULL_REQUEST, JSON_MEDIA, reqText);
186         assertEquals(reqText, response);
187
188         assertTrue(MyGsonProvider.hasReadSome());
189         assertTrue(MyGsonProvider.hasWrittenSome());
190
191         assertFalse(MyJacksonProvider.hasReadSome());
192         assertFalse(MyJacksonProvider.hasWrittenSome());
193
194         assertFalse(MyYamlProvider.hasReadSome());
195         assertFalse(MyYamlProvider.hasWrittenSome());
196     }
197
198     @Test
199     public void testYamlPackageServer() throws Exception {
200         logger.info("-- testYamlPackageServer() --");
201
202         HttpServletServer server = HttpServletServerFactoryInstance.getServerFactory()
203                         .build("echo", LOCALHOST, port, "/", false, true);
204
205         server.setSerializationProvider(MyYamlProvider.class.getName());
206         server.addServletPackage("/*", this.getClass().getPackage().getName());
207         server.addFilterClass("/*", TestFilter.class.getName());
208         server.waitedStart(5000);
209
210         assertTrue(HttpServletServerFactoryInstance.getServerFactory().get(port).isAlive());
211
212         RestEchoReqResp request = new RestEchoReqResp();
213         request.setRequestId(100);
214         request.setText(SOME_TEXT);
215         String reqText = new StandardYamlCoder().encode(request);
216
217         String response = http(portUrl + JUNIT_ECHO_FULL_REQUEST, YAML_MEDIA, reqText);
218
219         // response reader strips newlines, so we should, too, before comparing
220         assertEquals(reqText.replace("\n", ""), response);
221
222         assertTrue(MyYamlProvider.hasReadSome());
223         assertTrue(MyYamlProvider.hasWrittenSome());
224
225         assertFalse(MyGsonProvider.hasReadSome());
226         assertFalse(MyGsonProvider.hasWrittenSome());
227
228         assertFalse(MyJacksonProvider.hasReadSome());
229         assertFalse(MyJacksonProvider.hasWrittenSome());
230     }
231
232     @Test
233     public void testDefaultClassServer() throws Exception {
234         logger.info("-- testDefaultClassServer() --");
235
236         HttpServletServer server = HttpServletServerFactoryInstance.getServerFactory()
237                         .build("echo", LOCALHOST, port, "/", false, true);
238         server.addServletClass("/*", RestEchoService.class.getName());
239         server.addFilterClass("/*", TestFilter.class.getName());
240         server.waitedStart(5000);
241
242         assertTrue(HttpServletServerFactoryInstance.getServerFactory().get(port).isAlive());
243
244         RestEchoReqResp request = new RestEchoReqResp();
245         request.setRequestId(100);
246         request.setText(SOME_TEXT);
247         String reqText = gson.toJson(request);
248
249         String response = http(portUrl + JUNIT_ECHO_FULL_REQUEST, JSON_MEDIA, reqText);
250         assertEquals(reqText, response);
251     }
252
253     @Test
254     public void testJacksonClassServer() throws Exception {
255         logger.info("-- testJacksonClassServer() --");
256
257         HttpServletServer server = HttpServletServerFactoryInstance.getServerFactory()
258                         .build("echo", LOCALHOST, port, "/", false, true);
259         server.setSerializationProvider(MyJacksonProvider.class.getName());
260         server.addServletClass("/*", RestEchoService.class.getName());
261         server.addFilterClass("/*", TestFilter.class.getName());
262         server.waitedStart(5000);
263
264         assertTrue(HttpServletServerFactoryInstance.getServerFactory().get(port).isAlive());
265
266         RestEchoReqResp request = new RestEchoReqResp();
267         request.setRequestId(100);
268         request.setText(SOME_TEXT);
269         String reqText = gson.toJson(request);
270
271         String response = http(portUrl + JUNIT_ECHO_FULL_REQUEST, JSON_MEDIA, reqText);
272         assertEquals(reqText, response);
273
274         assertTrue(MyJacksonProvider.hasReadSome());
275         assertTrue(MyJacksonProvider.hasWrittenSome());
276
277         assertFalse(MyGsonProvider.hasReadSome());
278         assertFalse(MyGsonProvider.hasWrittenSome());
279
280         assertFalse(MyYamlProvider.hasReadSome());
281         assertFalse(MyYamlProvider.hasWrittenSome());
282     }
283
284     @Test
285     public void testGsonClassServer() throws Exception {
286         logger.info("-- testGsonClassServer() --");
287
288         HttpServletServer server = HttpServletServerFactoryInstance.getServerFactory()
289                         .build("echo", LOCALHOST, port, "/", false, true);
290         server.setSerializationProvider(MyGsonProvider.class.getName());
291         server.addServletClass("/*", RestEchoService.class.getName());
292         server.addFilterClass("/*", TestFilter.class.getName());
293         server.waitedStart(5000);
294
295         assertTrue(HttpServletServerFactoryInstance.getServerFactory().get(port).isAlive());
296
297         RestEchoReqResp request = new RestEchoReqResp();
298         request.setRequestId(100);
299         request.setText(SOME_TEXT);
300         String reqText = gson.toJson(request);
301
302         String response = http(portUrl + JUNIT_ECHO_FULL_REQUEST, JSON_MEDIA, reqText);
303         assertEquals(reqText, response);
304
305         assertTrue(MyGsonProvider.hasReadSome());
306         assertTrue(MyGsonProvider.hasWrittenSome());
307
308         assertFalse(MyJacksonProvider.hasReadSome());
309         assertFalse(MyJacksonProvider.hasWrittenSome());
310
311         assertFalse(MyYamlProvider.hasReadSome());
312         assertFalse(MyYamlProvider.hasWrittenSome());
313     }
314
315     @Test
316     public void testYamlClassServer() throws Exception {
317         logger.info("-- testYamlClassServer() --");
318
319         HttpServletServer server = HttpServletServerFactoryInstance.getServerFactory()
320                         .build("echo", LOCALHOST, port, "/", false, true);
321         server.setSerializationProvider(MyYamlProvider.class.getName());
322         server.addServletClass("/*", RestEchoService.class.getName());
323         server.addFilterClass("/*", TestFilter.class.getName());
324         server.waitedStart(5000);
325
326         assertTrue(HttpServletServerFactoryInstance.getServerFactory().get(port).isAlive());
327
328         RestEchoReqResp request = new RestEchoReqResp();
329         request.setRequestId(100);
330         request.setText(SOME_TEXT);
331         String reqText = new StandardYamlCoder().encode(request);
332
333         String response = http(portUrl + JUNIT_ECHO_FULL_REQUEST, YAML_MEDIA, reqText);
334
335         // response reader strips newlines, so we should, too, before comparing
336         assertEquals(reqText.replace("\n", ""), response);
337
338         assertTrue(MyYamlProvider.hasReadSome());
339         assertTrue(MyYamlProvider.hasWrittenSome());
340
341         assertFalse(MyGsonProvider.hasReadSome());
342         assertFalse(MyGsonProvider.hasWrittenSome());
343
344         assertFalse(MyJacksonProvider.hasReadSome());
345         assertFalse(MyJacksonProvider.hasWrittenSome());
346     }
347
348     @Test
349     public void testSerialize() {
350         HttpServletServer server = HttpServletServerFactoryInstance.getServerFactory()
351                         .build("echo", LOCALHOST, port, "/", false, true);
352         server.addServletPackage("/*", this.getClass().getPackage().getName());
353         server.addFilterClass("/*", TestFilter.class.getName());
354
355         // ensure we can serialize the server
356         assertThatCode(() -> new GsonTestUtils().compareGson(server, HttpServerTest.class)).doesNotThrowAnyException();
357     }
358
359     @Test
360     public void testSingleServer() throws Exception {
361         logger.info("-- testSingleServer() --");
362
363         HttpServletServer server = HttpServletServerFactoryInstance.getServerFactory()
364                         .build("echo", LOCALHOST, port, "/", false, true);
365         server.addServletPackage("/*", this.getClass().getPackage().getName());
366         server.addFilterClass("/*", TestFilter.class.getName());
367         server.waitedStart(5000);
368
369         assertTrue(HttpServletServerFactoryInstance.getServerFactory().get(port).isAlive());
370         assertFalse(HttpServletServerFactoryInstance.getServerFactory().get(port).isAaf());
371
372         String response = http(portUrl + JUNIT_ECHO_HELLO);
373         assertEquals(HELLO, response);
374
375         assertThatThrownBy(() -> http(portUrl + SWAGGER_JSON)).isInstanceOf(IOException.class);
376
377         response = http(portUrl + "/junit/echo/hello?block=true");
378         assertEquals("FILTERED", response);
379
380         assertTrue(HttpServletServerFactoryInstance.getServerFactory().get(port).isAlive());
381         assertEquals(1, HttpServletServerFactoryInstance.getServerFactory().inventory().size());
382
383         System.setProperty("cadi_longitude", "0.0");
384         System.setProperty("cadi_latitude", "0.0");
385         server.setAafAuthentication("/*");
386         assertTrue(HttpServletServerFactoryInstance.getServerFactory().get(port).isAaf());
387
388         HttpServletServerFactoryInstance.getServerFactory().destroy(port);
389         assertEquals(0, HttpServletServerFactoryInstance.getServerFactory().inventory().size());
390     }
391
392     @Test
393     public void testMultipleServers() throws Exception {
394         logger.info("-- testMultipleServers() --");
395
396         HttpServletServer server1 = HttpServletServerFactoryInstance.getServerFactory()
397                         .build("echo-1", false, LOCALHOST, port, "/", true, true);
398         server1.addServletPackage("/*", this.getClass().getPackage().getName());
399         server1.waitedStart(5000);
400
401         int port2 = port + 1;
402
403         HttpServletServer server2 = HttpServletServerFactoryInstance.getServerFactory()
404                         .build("echo-2", LOCALHOST, port2, "/", false, true);
405         server2.addServletPackage("/*", this.getClass().getPackage().getName());
406         server2.waitedStart(5000);
407
408         assertTrue(HttpServletServerFactoryInstance.getServerFactory().get(port).isAlive());
409         assertTrue(HttpServletServerFactoryInstance.getServerFactory().get(port2).isAlive());
410
411         String response = http(portUrl + JUNIT_ECHO_HELLO);
412         assertEquals(HELLO, response);
413
414         response = http(portUrl + SWAGGER_JSON);
415         assertNotNull(response);
416
417         response = http(LOCALHOST_PREFIX + port2 + JUNIT_ECHO_HELLO);
418         assertEquals(HELLO, response);
419
420         assertThatThrownBy(() -> http(LOCALHOST_PREFIX + port2 + SWAGGER_JSON)).isInstanceOf(IOException.class);
421
422         HttpServletServerFactoryInstance.getServerFactory().destroy();
423         assertTrue(HttpServletServerFactoryInstance.getServerFactory().inventory().isEmpty());
424     }
425
426     @Test
427     public void testMultiServicePackage() throws Exception {
428         logger.info("-- testMultiServicePackage() --");
429
430         String randomName = UUID.randomUUID().toString();
431
432         HttpServletServer server = HttpServletServerFactoryInstance.getServerFactory()
433                         .build(randomName, LOCALHOST, port, "/", false, true);
434         server.addServletPackage("/*", this.getClass().getPackage().getName());
435         server.waitedStart(5000);
436
437         assertTrue(HttpServletServerFactoryInstance.getServerFactory().get(port).isAlive());
438
439         String response = http(portUrl + JUNIT_ECHO_HELLO);
440         assertEquals(HELLO, response);
441
442         response = http(portUrl + "/junit/endpoints/http/servers");
443         assertTrue(response.contains(randomName));
444
445         HttpServletServerFactoryInstance.getServerFactory().destroy();
446         assertTrue(HttpServletServerFactoryInstance.getServerFactory().inventory().isEmpty());
447     }
448
449     @Test
450     public void testServiceClass() throws Exception {
451         logger.info("-- testServiceClass() --");
452         String randomName = UUID.randomUUID().toString();
453
454         HttpServletServer server = HttpServletServerFactoryInstance.getServerFactory()
455                         .build(randomName, LOCALHOST, port, "/", false, true);
456         server.addServletClass("/*", RestEchoService.class.getName());
457         server.waitedStart(5000);
458
459         assertTrue(HttpServletServerFactoryInstance.getServerFactory().get(port).isAlive());
460
461         String response = http(portUrl + JUNIT_ECHO_HELLO);
462         assertEquals(HELLO, response);
463
464         HttpServletServerFactoryInstance.getServerFactory().destroy();
465         assertTrue(HttpServletServerFactoryInstance.getServerFactory().inventory().isEmpty());
466     }
467
468     @Test
469     public void testMultiServiceClass() throws Exception {
470         logger.info("-- testMultiServiceClass() --");
471
472         String randomName = UUID.randomUUID().toString();
473
474         HttpServletServer server = HttpServletServerFactoryInstance.getServerFactory()
475                         .build(randomName, LOCALHOST, port, "/", false, true);
476         server.addServletClass("/*", RestEchoService.class.getName());
477         server.addServletClass("/*", RestEndpoints.class.getName());
478         server.waitedStart(5000);
479
480         assertTrue(HttpServletServerFactoryInstance.getServerFactory().get(port).isAlive());
481
482         String response = http(portUrl + JUNIT_ECHO_HELLO);
483         assertEquals(HELLO, response);
484
485         response = http(portUrl + "/junit/endpoints/http/servers");
486         assertTrue(response.contains(randomName));
487
488         HttpServletServerFactoryInstance.getServerFactory().destroy();
489         assertTrue(HttpServletServerFactoryInstance.getServerFactory().inventory().isEmpty());
490     }
491
492     @Test
493     public void testSingleStaticResourceServer() throws Exception {
494         logger.info("-- testSingleStaticResourceServer() --");
495
496         HttpServletServer staticServer = HttpServletServerFactoryInstance.getServerFactory()
497                 .buildStaticResourceServer("Static Resources Server", false, LOCALHOST, port, "/", true);
498         Throwable thrown = catchThrowable(() -> staticServer.addServletResource("/*", null));
499         assertThat(thrown).isInstanceOf(IllegalArgumentException.class)
500                 .hasMessageContaining("No resourceBase provided");
501
502         staticServer.addServletResource(null,
503                 HttpServerTest.class.getClassLoader().getResource("webapps/root").toExternalForm());
504
505         thrown = catchThrowable(() -> staticServer.addServletClass("/*", RestEchoService.class.getName()));
506         assertThat(thrown).isInstanceOf(UnsupportedOperationException.class)
507                 .hasMessageContaining("is not supported on this type of jetty server");
508
509         thrown = catchThrowable(() -> staticServer.addServletPackage("/api/*", this.getClass().getPackage().getName()));
510         assertThat(thrown).isInstanceOf(UnsupportedOperationException.class)
511                 .hasMessageContaining("is not supported on this type of jetty server");
512
513         thrown = catchThrowable(() -> staticServer.setSerializationProvider(MyGsonProvider.class.getName()));
514         assertThat(thrown).isInstanceOf(UnsupportedOperationException.class)
515                 .hasMessageContaining("is not supported on this type of jetty server");
516
517         staticServer.waitedStart(5000);
518
519         assertTrue(HttpServletServerFactoryInstance.getServerFactory().get(port).isAlive());
520         assertEquals(1, HttpServletServerFactoryInstance.getServerFactory().inventory().size());
521
522         String response = http(portUrl);
523         assertThat(response).contains("Test Jetty Static Resources Root");
524
525         HttpServletServerFactoryInstance.getServerFactory().destroy(port);
526         assertEquals(0, HttpServletServerFactoryInstance.getServerFactory().inventory().size());
527     }
528
529     @Test
530     public void testMultiStaticResourceServer() throws Exception {
531         logger.info("-- testMultiStaticResourceServer() --");
532
533         HttpServletServer staticResourceServer = HttpServletServerFactoryInstance.getServerFactory()
534                 .buildStaticResourceServer("Static Resources Server", false, LOCALHOST, port, "/", true);
535         staticResourceServer.addServletResource("/root/*",
536                 HttpServerTest.class.getClassLoader().getResource("webapps/root").toExternalForm());
537         staticResourceServer.addServletResource("/alt-root/*",
538                 HttpServerTest.class.getClassLoader().getResource("webapps/alt-root").toExternalForm());
539         staticResourceServer.waitedStart(5000);
540
541         assertTrue(HttpServletServerFactoryInstance.getServerFactory().get(port).isAlive());
542         assertEquals(1, HttpServletServerFactoryInstance.getServerFactory().inventory().size());
543
544         String response = http(portUrl + "/root/");
545         assertThat(response).contains("Test Jetty Static Resources Root");
546
547         response = http(portUrl + "/alt-root/");
548         assertThat(response).contains("Test Jetty Static Resources Alt-Root");
549
550         HttpServletServerFactoryInstance.getServerFactory().destroy(port);
551         assertEquals(0, HttpServletServerFactoryInstance.getServerFactory().inventory().size());
552     }
553
554     @Test
555     public void testMultiTypesServer() throws Exception {
556         logger.info("-- testMultiTypesServer() --");
557
558         HttpServletServer staticResourceServer = HttpServletServerFactoryInstance.getServerFactory()
559                 .buildStaticResourceServer("Static Resources Server", false, LOCALHOST, port, "/", true);
560         staticResourceServer.addServletResource("/root/*",
561                 HttpServerTest.class.getClassLoader().getResource("webapps/root").toExternalForm());
562         staticResourceServer.waitedStart(5000);
563
564         int port2 = port + 1;
565         HttpServletServer jerseyServer =
566                 HttpServletServerFactoryInstance.getServerFactory().build("echo", LOCALHOST, port2, "/", false, true);
567         jerseyServer.addServletPackage("/api/*", this.getClass().getPackage().getName());
568
569         Throwable thrown = catchThrowable(() -> jerseyServer.addServletResource("/root/*",
570                 HttpServerTest.class.getClassLoader().getResource("webapps/root").toExternalForm()));
571         assertThat(thrown).isInstanceOf(UnsupportedOperationException.class)
572                 .hasMessageContaining("is not supported on this type of jetty server");
573
574         jerseyServer.waitedStart(5000);
575
576         assertTrue(HttpServletServerFactoryInstance.getServerFactory().get(port).isAlive());
577         assertEquals(2, HttpServletServerFactoryInstance.getServerFactory().inventory().size());
578
579         String response = http(portUrl + "/root/");
580         assertThat(response).contains("Test Jetty Static Resources Root");
581
582         response = http(LOCALHOST_PREFIX + port2 + "/api" + JUNIT_ECHO_HELLO);
583         assertEquals(HELLO, response);
584
585         HttpServletServerFactoryInstance.getServerFactory().destroy();
586         assertEquals(0, HttpServletServerFactoryInstance.getServerFactory().inventory().size());
587     }
588
589     /**
590      * performs an http request.
591      *
592      * @throws MalformedURLException make sure URL is good
593      * @throws IOException thrown is IO exception occurs
594      * @throws InterruptedException thrown if thread interrupted occurs
595      */
596     private String http(String urlString)
597             throws IOException, InterruptedException {
598         URL url = new URL(urlString);
599         if (!NetworkUtil.isTcpPortOpen(url.getHost(), url.getPort(), 25, 100)) {
600             throw new IllegalStateException("port never opened: " + url);
601         }
602         return response(url.openConnection());
603     }
604
605     /**
606      * Performs an http request.
607      *
608      * @throws MalformedURLException make sure URL is good
609      * @throws IOException thrown is IO exception occurs
610      * @throws InterruptedException thrown if thread interrupted occurs
611      */
612     private String http(String urlString, String mediaType, String post)
613             throws IOException, InterruptedException {
614         URL url = new URL(urlString);
615         if (!NetworkUtil.isTcpPortOpen(url.getHost(), url.getPort(), 25, 100)) {
616             throw new IllegalStateException("port never opened: " + url);
617         }
618         HttpURLConnection conn = (HttpURLConnection) url.openConnection();
619         conn.setRequestMethod("POST");
620         conn.setDoOutput(true);
621         conn.setRequestProperty("Content-Type", mediaType);
622         conn.setRequestProperty("Accept", mediaType);
623         IOUtils.write(post, conn.getOutputStream(), StandardCharsets.UTF_8);
624         return response(conn);
625     }
626
627     /**
628      * gets http response.
629      *
630      * @param conn connection from which to read
631      *
632      * @throws IOException if an I/O error occurs
633      */
634     private String response(URLConnection conn) throws IOException {
635         try (InputStream inpstr = conn.getInputStream()) {
636             return String.join("", IOUtils.readLines(inpstr, StandardCharsets.UTF_8));
637         }
638     }
639
640 }