From 03d255d204c4bc1212c4aa7c8bb06080897ede8a Mon Sep 17 00:00:00 2001 From: Moritz Halbritter Date: Fri, 25 Nov 2022 13:56:17 +0100 Subject: [PATCH] Add webmvc-undertow-tls smoke test Closes gh-68 --- STATUS.adoc | 6 ++ ci/smoke-tests.yml | 3 + framework/webmvc-undertow-tls/README.adoc | 1 + framework/webmvc-undertow-tls/build.gradle | 25 ++++++ .../WebMvcUndertowTlsApplicationAotTests.java | 75 ++++++++++++++++++ .../src/appTest/resources/truststore.jks | Bin 0 -> 748 bytes .../webmvc/undertow/tls/TestController.java | 15 ++++ .../tls/WebMvcUndertowTlsApplication.java | 28 +++++++ .../src/main/resources/application.properties | 4 + .../src/main/resources/keystore.jks | Bin 0 -> 2035 bytes 10 files changed, 157 insertions(+) create mode 100644 framework/webmvc-undertow-tls/README.adoc create mode 100644 framework/webmvc-undertow-tls/build.gradle create mode 100644 framework/webmvc-undertow-tls/src/appTest/java/com/example/webmvc/undertow/tls/WebMvcUndertowTlsApplicationAotTests.java create mode 100644 framework/webmvc-undertow-tls/src/appTest/resources/truststore.jks create mode 100644 framework/webmvc-undertow-tls/src/main/java/com/example/webmvc/undertow/tls/TestController.java create mode 100644 framework/webmvc-undertow-tls/src/main/java/com/example/webmvc/undertow/tls/WebMvcUndertowTlsApplication.java create mode 100644 framework/webmvc-undertow-tls/src/main/resources/application.properties create mode 100644 framework/webmvc-undertow-tls/src/main/resources/keystore.jks diff --git a/STATUS.adoc b/STATUS.adoc index 964d066f..b5b72037 100644 --- a/STATUS.adoc +++ b/STATUS.adoc @@ -549,6 +549,12 @@ h|nativeTest |image:https://ci.spring.io/api/v1/teams/spring-aot-smoke-tests/pipelines/spring-aot-smoke-tests-1.0.x/jobs/webmvc-undertow-test/badge[link=https://ci.spring.io/teams/spring-aot-smoke-tests/pipelines/spring-aot-smoke-tests-1.0.x/jobs/webmvc-undertow-test] |image:https://ci.spring.io/api/v1/teams/spring-aot-smoke-tests/pipelines/spring-aot-smoke-tests-1.0.x/jobs/webmvc-undertow-native-test/badge[link=https://ci.spring.io/teams/spring-aot-smoke-tests/pipelines/spring-aot-smoke-tests-1.0.x/jobs/webmvc-undertow-native-test] +|webmvc-undertow-tls +|image:https://ci.spring.io/api/v1/teams/spring-aot-smoke-tests/pipelines/spring-aot-smoke-tests-1.0.x/jobs/webmvc-undertow-tls-app-test/badge[link=https://ci.spring.io/teams/spring-aot-smoke-tests/pipelines/spring-aot-smoke-tests-1.0.x/jobs/webmvc-undertow-tls-app-test] +|image:https://ci.spring.io/api/v1/teams/spring-aot-smoke-tests/pipelines/spring-aot-smoke-tests-1.0.x/jobs/webmvc-undertow-tls-native-app-test/badge[link=https://ci.spring.io/teams/spring-aot-smoke-tests/pipelines/spring-aot-smoke-tests-1.0.x/jobs/webmvc-undertow-tls-native-app-test] +| +| + |websocket-jetty |image:https://ci.spring.io/api/v1/teams/spring-aot-smoke-tests/pipelines/spring-aot-smoke-tests-1.0.x/jobs/websocket-jetty-app-test/badge[link=https://ci.spring.io/teams/spring-aot-smoke-tests/pipelines/spring-aot-smoke-tests-1.0.x/jobs/websocket-jetty-app-test] |image:https://ci.spring.io/api/v1/teams/spring-aot-smoke-tests/pipelines/spring-aot-smoke-tests-1.0.x/jobs/websocket-jetty-native-app-test/badge[link=https://ci.spring.io/teams/spring-aot-smoke-tests/pipelines/spring-aot-smoke-tests-1.0.x/jobs/websocket-jetty-native-app-test] diff --git a/ci/smoke-tests.yml b/ci/smoke-tests.yml index fa42d450..ddc6063f 100644 --- a/ci/smoke-tests.yml +++ b/ci/smoke-tests.yml @@ -267,6 +267,9 @@ groups: - name: webmvc-undertow app_test: true test: true + - name: webmvc-undertow-tls + app_test: true + test: false - name: websocket-jetty app_test: true test: false diff --git a/framework/webmvc-undertow-tls/README.adoc b/framework/webmvc-undertow-tls/README.adoc new file mode 100644 index 00000000..fc98a8f5 --- /dev/null +++ b/framework/webmvc-undertow-tls/README.adoc @@ -0,0 +1 @@ +Tests if WebMVC with Undertow with TLS is working diff --git a/framework/webmvc-undertow-tls/build.gradle b/framework/webmvc-undertow-tls/build.gradle new file mode 100644 index 00000000..7a165283 --- /dev/null +++ b/framework/webmvc-undertow-tls/build.gradle @@ -0,0 +1,25 @@ +plugins { + id 'java' + id 'org.springframework.boot' + id 'org.springframework.aot.smoke-test' + id 'org.graalvm.buildtools.native' +} + +dependencies { + implementation(platform(org.springframework.boot.gradle.plugin.SpringBootPlugin.BOM_COORDINATES)) + implementation("org.springframework.boot:spring-boot-starter-web") + implementation("org.springframework.boot:spring-boot-starter-undertow") + modules { + module("org.springframework.boot:spring-boot-starter-tomcat") { + replacedBy("org.springframework.boot:spring-boot-starter-undertow", "Use Undertow instead of Tomcat") + } + } + + testImplementation("org.springframework.boot:spring-boot-starter-test") + + appTestImplementation(project(":aot-smoke-test-support")) +} + +aotSmokeTest { + webApplication = true +} diff --git a/framework/webmvc-undertow-tls/src/appTest/java/com/example/webmvc/undertow/tls/WebMvcUndertowTlsApplicationAotTests.java b/framework/webmvc-undertow-tls/src/appTest/java/com/example/webmvc/undertow/tls/WebMvcUndertowTlsApplicationAotTests.java new file mode 100644 index 00000000..7cb6f115 --- /dev/null +++ b/framework/webmvc-undertow-tls/src/appTest/java/com/example/webmvc/undertow/tls/WebMvcUndertowTlsApplicationAotTests.java @@ -0,0 +1,75 @@ +/* + * Copyright 2022 the original author or authors. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * https://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.example.webmvc.undertow.tls; + +import java.io.InputStream; +import java.net.URI; +import java.net.http.HttpClient; +import java.security.KeyStore; + +import javax.net.ssl.SSLContext; +import javax.net.ssl.TrustManagerFactory; + +import org.junit.jupiter.api.Test; + +import org.springframework.aot.smoketest.support.junit.ApplicationTest; +import org.springframework.aot.smoketest.support.junit.ApplicationUrl; +import org.springframework.aot.smoketest.support.junit.ApplicationUrl.Scheme; +import org.springframework.http.client.reactive.ClientHttpConnector; +import org.springframework.http.client.reactive.JdkClientHttpConnector; +import org.springframework.test.web.reactive.server.WebTestClient; + +import static org.assertj.core.api.Assertions.assertThat; + +@ApplicationTest +class WebMvcUndertowTlsApplicationAotTests { + + @Test + void stringResponseBody(@ApplicationUrl(scheme = Scheme.HTTPS) URI applicationUrl) throws Exception { + WebTestClient client = buildWebClient(applicationUrl); + + client.get().exchange().expectStatus().isOk().expectBody().consumeWith( + (result) -> assertThat(new String(result.getResponseBodyContent())).isEqualTo("Hello World TLS")); + } + + /** + * Builds a web client for the running application. This web client is configured to + * trust the TLS certificate of the server. + * @param applicationUrl the URL to the application + * @return web client + * @throws Exception if something went wrong + */ + private static WebTestClient buildWebClient(URI applicationUrl) throws Exception { + KeyStore trustStore = KeyStore.getInstance("jks"); + try (InputStream stream = WebMvcUndertowTlsApplicationAotTests.class.getResourceAsStream("/truststore.jks")) { + assertThat(stream).as("Trust store on test classpath").isNotNull(); + trustStore.load(stream, null); + } + + TrustManagerFactory trustManagerFactory = TrustManagerFactory + .getInstance(TrustManagerFactory.getDefaultAlgorithm()); + trustManagerFactory.init(trustStore); + + SSLContext sslContext = SSLContext.getInstance("TLS"); + sslContext.init(null, trustManagerFactory.getTrustManagers(), null); + + HttpClient httpClient = HttpClient.newBuilder().sslContext(sslContext).build(); + ClientHttpConnector connector = new JdkClientHttpConnector(httpClient); + return WebTestClient.bindToServer(connector).baseUrl(applicationUrl.toString()).build(); + } + +} diff --git a/framework/webmvc-undertow-tls/src/appTest/resources/truststore.jks b/framework/webmvc-undertow-tls/src/appTest/resources/truststore.jks new file mode 100644 index 0000000000000000000000000000000000000000..063186744ce50a70bf1d010c16d4e6a8b0abc04e GIT binary patch literal 748 zcmezO_TO6u1_mY|W(3omIr+(nIT`uIB|wp;+BD@L2G$5YQv*w&qE!Y>Ov?@5qwPB{BO^B}gMo;lkbwXjb0`Zl55gz|1#w;@BLfQq3qvCV zb5qkO34S9(6agIini!RkEnsA2U~XdMX8^i^i>Zl`kzvXAhkEWW;|@&Hd0-Q}Z>zce z%&5Z}Q}Z@|$ygaS<=;h_bvc%Tiw!l`Je@D36RrE=Qt$_yOZe zA&nP0Pp&-t_V6If>F7mCC+0t>2{XSc`>&t-Y1};7w>v&Q;Vqh4yR=MdjohUPS0i?5 z2$if>+Yps*Tx&1*ut!mQXVFhtt{b6Ef1?5xM)h3_88cg6&XqO9Z%_3soAy6G6B`~U9%*mZZaq`A<^N5_bCa0a{_)4?ze_*5 zeB0N%A1=*mwLh>m$ouAOzW3saNm~r(n6~}$z4CsM<5q!rG3Jwg?elDZ%f!scz=#|| zz$gHQ5F>;9{NxJFFY68^ct4u*|F^pK3l*0|-_8VG5`XHfVO%F>TpGGUcuK#^i6y^P zLZc>}THNdMY$LnVntRiKWp%6U5LrnBqbsDIq?8MsW@N& literal 0 HcmV?d00001 diff --git a/framework/webmvc-undertow-tls/src/main/java/com/example/webmvc/undertow/tls/TestController.java b/framework/webmvc-undertow-tls/src/main/java/com/example/webmvc/undertow/tls/TestController.java new file mode 100644 index 00000000..7d352024 --- /dev/null +++ b/framework/webmvc-undertow-tls/src/main/java/com/example/webmvc/undertow/tls/TestController.java @@ -0,0 +1,15 @@ +package com.example.webmvc.undertow.tls; + +import org.springframework.http.MediaType; +import org.springframework.web.bind.annotation.GetMapping; +import org.springframework.web.bind.annotation.RestController; + +@RestController +public class TestController { + + @GetMapping(value = "/", produces = MediaType.TEXT_PLAIN_VALUE) + public String index() { + return "Hello World TLS"; + } + +} diff --git a/framework/webmvc-undertow-tls/src/main/java/com/example/webmvc/undertow/tls/WebMvcUndertowTlsApplication.java b/framework/webmvc-undertow-tls/src/main/java/com/example/webmvc/undertow/tls/WebMvcUndertowTlsApplication.java new file mode 100644 index 00000000..438c2216 --- /dev/null +++ b/framework/webmvc-undertow-tls/src/main/java/com/example/webmvc/undertow/tls/WebMvcUndertowTlsApplication.java @@ -0,0 +1,28 @@ +package com.example.webmvc.undertow.tls; + +import com.example.webmvc.undertow.tls.WebMvcUndertowTlsApplication.KeyStoreRuntimeHints; + +import org.springframework.aot.hint.RuntimeHints; +import org.springframework.aot.hint.RuntimeHintsRegistrar; +import org.springframework.boot.SpringApplication; +import org.springframework.boot.autoconfigure.SpringBootApplication; +import org.springframework.context.annotation.ImportRuntimeHints; + +@SpringBootApplication +@ImportRuntimeHints(KeyStoreRuntimeHints.class) +public class WebMvcUndertowTlsApplication { + + public static void main(String[] args) { + SpringApplication.run(WebMvcUndertowTlsApplication.class, args); + } + + static class KeyStoreRuntimeHints implements RuntimeHintsRegistrar { + + @Override + public void registerHints(RuntimeHints hints, ClassLoader classLoader) { + hints.resources().registerPattern("keystore.jks"); + } + + } + +} diff --git a/framework/webmvc-undertow-tls/src/main/resources/application.properties b/framework/webmvc-undertow-tls/src/main/resources/application.properties new file mode 100644 index 00000000..b2dbf04e --- /dev/null +++ b/framework/webmvc-undertow-tls/src/main/resources/application.properties @@ -0,0 +1,4 @@ +server.ssl.key-store=classpath:keystore.jks +server.ssl.key-store-password=secret +server.ssl.key-alias=localhost +server.ssl.key-password=secret diff --git a/framework/webmvc-undertow-tls/src/main/resources/keystore.jks b/framework/webmvc-undertow-tls/src/main/resources/keystore.jks new file mode 100644 index 0000000000000000000000000000000000000000..cad0ed8dfd0e80a7bfc3ed3fe5e77db5841735ab GIT binary patch literal 2035 zcmZ{kXH*gjAI1R@!wqU~MUM+dfde#2GR-v2ycSZp5-mY;l%(dsb;EJhTrCF<)Kbfl zt1`75Wu~cIt+q-R#biI8l30HXtB-X6KO?L4ntLpMpR#!km=RKv6}j>86jX!lS!HEaXkD&z zy_8wZ3^NZl0jFh=PYw9msPv0|s8+7ww`}>Jv(2Nw{bKI&3mv7MLLQi~v1Qpd`ue!4 z_dhsSH%<(Cpx+2wRe4`FQ9%(l^jz_8!i?ew{O~Yxs2d{HTh4?u*ZV_rr899JY{2LZ zc>(PhmWs|xTHVGdlf^V6XY6WWux=NL;|o!SD@EsV(Dk^RhD6wRz<_8-fW)IS=@Iaz z-)nB&0rleiS=US2WS!;sCMI-%AVbrWd= z=F1z7+z|xc@Ua7fC9SfWUPQQyUg(q%BHPX*I8vYCW#M_b>`r{ojs7>GK}KB;CK}h2laGIvFIeDqY{LO5Zq70V#qqIe%uVF$uMcaO zD)LULeJ(saKJjVKfd>qTK-Y}Y*3|foeC(DCqT-EqgpX0p7x9j=uODQ!(DpX#W_Io3 zU4+Z8w&M#jm>G^o8kOKq{Fhkb8%Rz8(Y~=aYr~G#R2=Pr`Qu8%S--Z)uR-;Mz(*%% zON7U%BeUXTLh_9fDi8Mo;qsd!ZH$$FOJASv>j4gqTJTqnSX_ADo%+{1t_Ni*RA+9; zdU;Q2j%2FPWDSRgoZ*iS<1ZuF`%gy0*8&pq<3ji5ivHI8)xgh-{=^Tjpq)>;H7=l? zU9SHk@vJuI&cVT~T3c^VwI@z5*`=3+U1kus*8 z_uXUpWZ!h#wTAiGj{ynDtf&HQo(8r(n2|#JCg+Tqs$tRWSLNwePaJ^uj^#~;ps^un zbY}<0d%voK1ifpd&&-3&Cd}NRCnXf{$GG4$?pFm^tjBtmF0f7>t0F*o$j*^9l5Wpgm|0602p(tf)in2sm zqD@g)3k#Bxj4As6jQ_|b0k!{qU>Ck3NkAFE?hoRiBp?t_A(+~C^pnriT;oZccV`P0 zf1A`}a6P1Hg;MR2FC0~?yI=)lqmlRKO5nzxCJWz3XOW{5{s$woPXerefqEu^)o_Ca zivdMC8e5Ez7_1liq~*`HEr6c%(ofgBqYsf# zuR=|YBci8VpTrd4Qnp-j5@!5*Q<9CY4n{ZcaDlILMIb^Mul?Tw`|h-^eq81hT*W_a zad+kxN-rsDk(<#)7R-&~V@u_>EwU^xZ0<&cQ*Bn7If^(e+{~G6zA*=%ouykE)(v`T43ueKJQGXIg4m^PJn;Mn$>wI;Tsj2VxiN*^pl?(6ZEiEskc<){vrWuA8OWc;!hVv*D^y zhFqN7@E`46x>cUqluFIYJl|7q?-!oa5BMyAk?7Q@JygC@%-pwJHCoJsZd9bRkFi`y MV9F9+o&W6c-|8rsO8@`> literal 0 HcmV?d00001