Как правильно импортировать самоподписанный сертификат в хранилище ключей Java, доступное для всех приложений Java по умолчанию?

Я хочу импортировать сам подписанный сертификат в Java, поэтому любое приложение Java, которое попытается установить SSL-соединение, будет доверять этому сертификату.

До сих пор мне удалось импортировать его в

keytool -import -trustcacerts -noprompt -storepass changeit -alias $REMHOST -file $REMHOST.pem
keytool -import -trustcacerts -noprompt -keystore cacerts -storepass changeit -alias $REMHOST -file $REMHOST.pem

Тем не менее, когда я пытаюсь запустить HTTPSClient.class, я все равно получаю:

javax.net.ssl.SSLHandshakeException: sun.security.validator.ValidatorException: PKIX path building failed: sun.security.provider.certpath.SunCertPathBuilderException: unable to find valid certification path to requested target

Ответ 1

В Windows самый простой способ - использовать программу portecle.

  • Загрузите и установите portecle.
  • Сначала сделайте 100% уверенным, что знаете, какой JRE или JDK используется для запуска вашей программы. На 64-битной Windows 7 может быть довольно много JRE. Process Explorer может помочь вам в этом или вы можете использовать: System.out.println(System.getProperty("java.home"));
  • Скопируйте файл JAVA_HOME\lib\security\cacerts в другую папку.
  • В Portecle щелкните File > Open Keystore File
  • Выберите файл cacerts
  • Введите этот пароль: changeit
  • Нажмите "Сервис" > "Импорт доверенного сертификата"
  • Просмотр файла mycertificate.pem
  • Нажмите "Импорт"
  • Нажмите "ОК" для предупреждения о пути доверия.
  • Нажмите "ОК", когда отобразится информация о сертификате.
  • Нажмите "Да", чтобы подтвердить сертификат как надежный.
  • Когда он запрашивает псевдоним, нажмите "ОК" и снова нажмите "ОК", когда он скажет, что он импортировал сертификат.
  • Нажмите "Сохранить". Не забывайте об этом или изменение отбрасывается.
  • Скопируйте файл cacerts обратно там, где вы его нашли.

В Linux:

Вы можете загрузить сертификат SSL с веб-сервера, который уже использует его следующим образом:

$ echo -n | openssl s_client -connect www.example.com:443 | \
   sed -ne '/-BEGIN CERTIFICATE-/,/-END CERTIFICATE-/p' > /tmp/examplecert.crt

Дополнительно проверьте информацию сертификата:

$ openssl x509 -in /tmp/examplecert.crt -text

Импортируйте сертификат в хранилище хранилищ Java cacerts:

$ keytool -import -trustcacerts -keystore /opt/java/jre/lib/security/cacerts \
   -storepass changeit -noprompt -alias mycert -file /tmp/examplecert.crt

Edit:

В наши дни нам часто не нужно добавлять сертификат в хранилище ключей, потому что вы можете получить сертификат за 5 долларов США в год от ssls.com. На всякий случай это вариант для вас.

Ответ 2

В итоге я написал небольшой script, который добавляет сертификаты в хранилища ключей, поэтому его гораздо проще использовать.

Вы можете получить последнюю версию https://github.com/ssbarnea/keytool-trust

#!/bin/bash
# version 1.0
# https://github.com/ssbarnea/keytool-trust
REMHOST=$1
REMPORT=${2:-443}

KEYSTORE_PASS=changeit
KEYTOOL="sudo keytool"

# /etc/java-6-sun/security/cacerts

for CACERTS in  /usr/lib/jvm/java-8-oracle/jre/lib/security/cacerts \
    /usr/lib/jvm/java-7-oracle/jre/lib/security/cacerts \
    "/System/Library/Java/JavaVirtualMachines/1.6.0.jdk/Contents/Home/lib/security/cacerts" \
    "/Applications/Xcode.app/Contents/Applications/Application Loader.app/Contents/MacOS/itms/java/lib/security/cacerts"
do

if [ -e "$CACERTS" ]
then
    echo --- Adding certs to $CACERTS

# FYI: the default keystore is located in ~/.keystore

if [ -z "$REMHOST" ]
    then
    echo "ERROR: Please specify the server name to import the certificatin from, eventually followed by the port number, if other than 443."
    exit 1
    fi

set -e

rm -f $REMHOST:$REMPORT.pem

if openssl s_client -connect $REMHOST:$REMPORT 1>/tmp/keytool_stdout 2>/tmp/output </dev/null
        then
        :
        else
        cat /tmp/keytool_stdout
        cat /tmp/output
        exit 1
        fi

if sed -ne '/-BEGIN CERTIFICATE-/,/-END CERTIFICATE-/p' </tmp/keytool_stdout > /tmp/$REMHOST:$REMPORT.pem
        then
        :
        else
        echo "ERROR: Unable to extract the certificate from $REMHOST:$REMPORT ($?)"
        cat /tmp/output
        fi

if $KEYTOOL -list -storepass ${KEYSTORE_PASS} -alias $REMHOST:$REMPORT >/dev/null
    then
    echo "Key of $REMHOST already found, skipping it."
    else
    $KEYTOOL -import -trustcacerts -noprompt -storepass ${KEYSTORE_PASS} -alias $REMHOST:$REMPORT -file /tmp/$REMHOST:$REMPORT.pem
    fi

if $KEYTOOL -list -storepass ${KEYSTORE_PASS} -alias $REMHOST:$REMPORT -keystore "$CACERTS" >/dev/null
    then
    echo "Key of $REMHOST already found in cacerts, skipping it."
    else
    $KEYTOOL -import -trustcacerts -noprompt -keystore "$CACERTS" -storepass ${KEYSTORE_PASS} -alias $REMHOST:$REMPORT -file /tmp/$REMHOST:$REMPORT.pem
    fi

fi

done

`` `

Ответ 3

    D:\Java\jdk1.5.0_10\bin\keytool -import -file "D:\Certificates\SDS services\Dev\dev-sdsservices-was8.infavig.com.cer" -keystore "D:\Java\jdk1.5.0_10\jre\lib\security\cacerts" -alias "sds certificate"

Ответ 4

Если вы используете сертификат, подписанный центром сертификации, который по умолчанию не включен в файл Java cacerts, вам необходимо выполнить следующую конфигурацию для соединений HTTPS. Чтобы импортировать сертификаты в cacerts:

  • Откройте проводник Windows и перейдите к файлу cacerts, который находится в подпапке jre\lib\security, в которой установлен AX Core Client. По умолчанию используется C:\Program Files\ACL Software\AX Core Client\jre\lib\security
  • Создайте резервную копию файла перед внесением любых изменений.
  • В зависимости от сертификатов, которые вы получаете от центра сертификации, который вы используете, вам может потребоваться импортировать промежуточный сертификат и/или корневой сертификат в файл cacerts. Для импорта сертификатов используйте следующий синтаксис: keytool -import -alias -keystore -trustcacerts -file
  • Если вы импортируете оба сертификата, псевдоним, указанный для каждого сертификата, должен быть уникальным.
  • Введите пароль для хранилища ключей в строке "Пароль" и нажмите "Enter". Пароль по умолчанию для файла cacerts - "changeit". Введите "y" в "Доверять этому сертификату"? и нажмите Enter.

Ответ 5

Это сработало для меня.:)

sudo keytool -importcert -file filename.cer -alias randomaliasname -keystore $JAVA_HOME/jre/lib/security/cacerts -storepass changeit 

Ответ 6

Возможно, вы захотите попробовать

keytool -import -trustcacerts -noprompt -keystore <full path to cacerts> -storepass changeit -alias $REMHOST -file $REMHOST.pem

я честно понятия не имею, где он помещает ваш сертификат, если вы просто пишете cacerts, просто дайте ему полный путь

Ответ 7

Простая команда "keytool" также работает на Windows и/или с Cygwin.

Если вы используете Cygwin, вот измененная команда, которую я использовал в нижней части ответа "S.Botha":

  • убедитесь, что вы идентифицируете JRE внутри JDK, который вы будете использовать
  • Запустите приглашение /cygwin как admin
  • зайдите в каталог bin этого JDK, например. cd/cygdrive/c/Program\Files/Java/jdk1.8.0_121/jre/bin
  • Выполните команду keytool изнутри, где вы указываете путь к вашему новому Cert в конце, например:

    ./keytool.exe -import -trustcacerts -keystore ../lib/security/cacerts  -storepass changeit -noprompt -alias myownaliasformysystem -file "D:\Stuff\saved-certs\ca.cert"
    

Обратите внимание, потому что если это находится под Cygwin, вы даете путь к программе, отличной от Cygwin, поэтому путь DOS-подобный и в кавычках.