Skip to content

Commit

Permalink
Create HTTPS tests with JNH connector #5169
Browse files Browse the repository at this point in the history
Signed-off-by: Jorge Bescos Gascon <jorge.bescos.gascon@oracle.com>
  • Loading branch information
jbescos committed Sep 27, 2022
1 parent 9ea156c commit 7075a78
Show file tree
Hide file tree
Showing 6 changed files with 225 additions and 0 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,104 @@
/*
* Copyright (c) 2022 Oracle and/or its affiliates. All rights reserved.
*
* This program and the accompanying materials are made available under the
* terms of the Eclipse Public License v. 2.0, which is available at
* http://www.eclipse.org/legal/epl-2.0.
*
* This Source Code may also be made available under the following Secondary
* Licenses when the conditions for such availability set forth in the
* Eclipse Public License v. 2.0 are satisfied: GNU General Public License,
* version 2 with the GNU Classpath Exception, which is available at
* https://www.gnu.org/software/classpath/license.html.
*
* SPDX-License-Identifier: EPL-2.0 OR GPL-2.0 WITH Classpath-exception-2.0
*/

package org.glassfish.jersey.jnh.connector;

import static org.junit.Assert.assertEquals;

import java.io.IOException;
import java.net.URI;
import java.util.Optional;
import java.util.logging.Logger;

import javax.net.ssl.SSLContext;
import javax.net.ssl.SSLParameters;

import org.glassfish.jersey.client.ClientConfig;
import org.glassfish.jersey.logging.LoggingFeature;
import org.glassfish.jersey.server.ResourceConfig;
import org.glassfish.jersey.test.JerseyTest;
import org.glassfish.jersey.test.grizzly.GrizzlyTestContainerFactory;
import org.glassfish.jersey.test.spi.TestContainerFactory;
import org.junit.Test;

import jakarta.ws.rs.GET;
import jakarta.ws.rs.Path;
import jakarta.ws.rs.client.Client;
import jakarta.ws.rs.client.ClientBuilder;
import jakarta.ws.rs.core.Application;
import jakarta.ws.rs.core.Response;
import jakarta.ws.rs.core.UriBuilder;

public class HttpsTest extends JerseyTest {

private static final Logger LOGGER = Logger.getLogger(HttpsTest.class.getName());
private static final String ROOT_PATH = "test";

@Path(ROOT_PATH)
public static class Resource {
@GET
public String get() {
return "GET";
}
}

@Override
protected TestContainerFactory getTestContainerFactory() {
return new GrizzlyTestContainerFactory();
}

@Override
protected URI getBaseUri() {
return UriBuilder.fromUri("https://localhost").port(getPort()).build();
}

@Override
protected Application configure() {
ResourceConfig config = new ResourceConfig(Resource.class);
config.register(new LoggingFeature(LOGGER, LoggingFeature.Verbosity.PAYLOAD_ANY));
return config;
}

@Override
protected Optional<SSLContext> getSslContext() {
return Optional.of(SslUtils.createServerSslContext(true, true));
}

@Override
protected Optional<SSLParameters> getSslParameters() {
SSLParameters serverSslParameters = new SSLParameters();
serverSslParameters.setNeedClientAuth(true);
return Optional.of(serverSslParameters);
}

private SSLContext clientSslContext() {
return SslUtils.createClientSslContext(true, true);
}

@Test
public void testConnection() throws IOException {
ClientConfig cc = new ClientConfig()
.connectorProvider(new JavaNetHttpConnectorProvider());
Client client = ClientBuilder.newBuilder()
.withConfig(cc)
.sslContext(clientSslContext())
.register(LoggingFeature.class)
.build();
Response response = client.target(getBaseUri()).path(ROOT_PATH).request().get();
assertEquals(200, response.getStatus());
assertEquals("GET", response.readEntity(String.class));
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,121 @@
/*
* Copyright (c) 2022 Oracle and/or its affiliates. All rights reserved.
*
* This program and the accompanying materials are made available under the
* terms of the Eclipse Public License v. 2.0, which is available at
* http://www.eclipse.org/legal/epl-2.0.
*
* This Source Code may also be made available under the following Secondary
* Licenses when the conditions for such availability set forth in the
* Eclipse Public License v. 2.0 are satisfied: GNU General Public License,
* version 2 with the GNU Classpath Exception, which is available at
* https://www.gnu.org/software/classpath/license.html.
*
* SPDX-License-Identifier: EPL-2.0 OR GPL-2.0 WITH Classpath-exception-2.0
*/

package org.glassfish.jersey.jnh.connector;

import javax.net.ssl.KeyManager;
import javax.net.ssl.KeyManagerFactory;
import javax.net.ssl.SSLContext;
import javax.net.ssl.TrustManager;
import javax.net.ssl.TrustManagerFactory;
import java.io.InputStream;
import java.security.KeyStore;

public final class SslUtils {

private static final String SERVER_IDENTITY_PATH = "server-identity.jks";
private static final char[] SERVER_IDENTITY_PASSWORD = "secret".toCharArray();
private static final String SERVER_TRUSTSTORE_PATH = "server-truststore.jks";
private static final char[] SERVER_TRUSTSTORE_PASSWORD = "secret".toCharArray();

private static final String CLIENT_IDENTITY_PATH = "client-identity.jks";
private static final char[] CLIENT_IDENTITY_PASSWORD = "secret".toCharArray();
private static final String CLIENT_TRUSTSTORE_PATH = "client-truststore.jks";
private static final char[] CLIENT_TRUSTSTORE_PASSWORD = "secret".toCharArray();

private static final String KEYSTORE_TYPE = "PKCS12";

private SslUtils() {}

public static SSLContext createServerSslContext(boolean includeKeyMaterial, boolean includeTrustMaterial) {
return createSslContext(
includeKeyMaterial,
includeTrustMaterial,
SERVER_IDENTITY_PATH,
SERVER_IDENTITY_PASSWORD,
SERVER_TRUSTSTORE_PATH,
SERVER_TRUSTSTORE_PASSWORD
);
}

public static SSLContext createClientSslContext(boolean includeKeyMaterial, boolean includeTrustMaterial) {
return createSslContext(
includeKeyMaterial,
includeTrustMaterial,
CLIENT_IDENTITY_PATH,
CLIENT_IDENTITY_PASSWORD,
CLIENT_TRUSTSTORE_PATH,
CLIENT_TRUSTSTORE_PASSWORD
);
}

private static SSLContext createSslContext(
boolean includeKeyMaterial,
boolean includeTrustMaterial,
String keyStorePath,
char[] keyStorePassword,
String trustStorePath,
char[] trustStorePassword) {

try {
KeyManager[] keyManagers = null;
TrustManager[] trustManagers = null;

if (includeKeyMaterial) {
keyManagers = createKeyManagers(keyStorePath, keyStorePassword);
}

if (includeTrustMaterial) {
trustManagers = createTrustManagers(trustStorePath, trustStorePassword);
}

SSLContext sslContext = SSLContext.getInstance("TLS");
sslContext.init(keyManagers, trustManagers, null);
return sslContext;
} catch (Exception e) {
throw new RuntimeException(e);
}
}

private static TrustManager[] createTrustManagers(String keyStorePath, char[] keyStorePassword) throws Exception {
KeyStore trustStore = getKeyStore(keyStorePath, keyStorePassword);

TrustManagerFactory trustManagerFactory = TrustManagerFactory.getInstance(TrustManagerFactory.getDefaultAlgorithm());
trustManagerFactory.init(trustStore);
return trustManagerFactory.getTrustManagers();
}

private static KeyManager[] createKeyManagers(String keyStorePath, char[] keyStorePassword) throws Exception {
KeyStore keyStore = getKeyStore(keyStorePath, keyStorePassword);

KeyManagerFactory keyManagerFactory = KeyManagerFactory.getInstance(KeyManagerFactory.getDefaultAlgorithm());
keyManagerFactory.init(keyStore, keyStorePassword);
return keyManagerFactory.getKeyManagers();
}

private static KeyStore getKeyStore(String path, char[] keyStorePassword) throws Exception {
try (InputStream inputStream = getResource(path)) {
KeyStore keyStore = KeyStore.getInstance(KEYSTORE_TYPE);
keyStore.load(inputStream, keyStorePassword);
return keyStore;
}
}

private static InputStream getResource(String path) {
return SslUtils.class.getClassLoader().getResourceAsStream(path);
}

}
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.

0 comments on commit 7075a78

Please sign in to comment.