Обзор
JSSE позволяет пользователям предоставлять доверенные хранилища и хранилища ключей по умолчанию, задав параметры javax.net.ssl. *. Я хотел бы предоставить для своего приложения TrustManager не по умолчанию, позволяя пользователю указывать KeyManager как обычно, но, похоже, нет никакого способа добиться этого.
Подробности
Предположим, на машинах unix я хочу разрешить пользователю использовать хранилище ключей pkcs12 для аутентификации, а на OS X я хочу разрешить пользователю использовать системную цепочку ключей. В OS X приложение можно запустить следующим образом:
java -Djavax.net.ssl.keyStore=NONE -Djavax.net.ssl.keyStoreType=KeychainStore \
-Djavax.net.ssl.keyStorePassword=- -jar MyApplication.jar
Это будет работать нормально: когда приложение обращается к https-серверу, который требует взаимной аутентификации (аутентификации сертификата клиента), пользователю будет предложено разрешить доступ к своей цепочке ключей.
Эта проблема
Теперь предположим, что я хочу связать самоподписанный центр сертификации с моим приложением. Я могу переопределить диспетчер доверия по умолчанию, создав TrustManagerFactory и передав хранилище ключей, содержащее мой сертификат (javadoc). Однако, чтобы использовать этот нестандартный диспетчер доверия, мне нужно создать и инициализировать SSLContext. Вот в чем проблема.
SSLContexts инициализируются вызовом init (..) и передать как KeyManager, так и TrustManager. Однако логика для создания KeyManager с использованием параметров javax.net.ssl. * Встроена в реализацию SSLContexts по умолчанию - я не могу найти способ получить KeyManager или KeyManagerFactory с использованием поведения по умолчанию, а также указать не по умолчанию TrustManager или TrustManagerFactory. Таким образом, кажется, что невозможно использовать, например, соответствующую реализацию цепочки ключей для конкретной операционной системы, одновременно предоставляя корневой сертификат для аутентификации удаленных серверов.