TLS/SSL avec Undertow


Undertow est un serveur Web Java avec lequel il est facile de démarrer.

Le support de SSL apporte un léger surplus de compléxité. Juste quelques lignes de code.

Certificat

Undertow utilise la classe java.security.Keystore. C'est donc elle qui impose les formats supportés.

C'est donc naturellement que Undertow supporte des certificats de type

Dans l'exemple ci-dessous, j'ai utilisé un certificat PKCS12 généré comme ceci :

openssl req -newkey RSA:2048 -nodes -keyout undertow.key -x509 -days 365 -out undertow.crt
openssl pkcs12 -inkey undertow.key -in undertow.crt -export -out undertow.pfx
rm undertow.key && rm undertow.crt

J'ai ensuite placé le fichier undertow.pfx dans le répertoire resources de mon projet afin qu'il se retrouve à la racine du fichier jar construit.

Démarrage

Au démarrage, au lieu du HttpListener, il faut ajouter un HttpsListener avec un context SSL qui contient le certificat.

   public static void main(final String[] args) throws Exception {
       ClassLoader classLoader = Thread.currentThread().getContextClassLoader();
       
       KeyStore keyStore = KeyStore.getInstance(KEYSTORE_TYPE);
       keyStore.load(
               classLoader.getResourceAsStream(KEYSTORE_FILE),
               KEYSTORE_PASSWORD.toCharArray());
       KeyManagerFactory keyManagerFactory = KeyManagerFactory.getInstance(KeyManagerFactory.getDefaultAlgorithm());
       keyManagerFactory.init(keyStore, KEYSTORE_PASSWORD.toCharArray());
       
       SSLContext sslContext = SSLContext.getInstance(TLS_VERSION);
       sslContext.init(keyManagerFactory.getKeyManagers(), null, null);
       
       Undertow sslServer = Undertow.builder()
               .addHttpsListener(8001, "localhost", sslContext)
               .setHandler(Start::hello)
               .build();
       sslServer.start();
   }