Как сгенерировать самоподписанный сертификат с помощью OpenSSL на Linux | UNLIX

Как сгенерировать самоподписанный сертификат с помощью OpenSSL на Linux | UNLIX Сертификаты

17 ответов

Лучший ответ

Вы можете сделать это одной командой:

openssl req -x509 -newkey rsa:4096 -keyout key.pem -out cert.pem -days 365

Вы также можете добавить -nodes (сокращение от no DES), если вы не хотите защищать свой закрытый ключ парольной фразой. В противном случае вам будет предложено ввести пароль «не менее 4 символов».

Параметр days (365) можно заменить любым числом, чтобы повлиять на срок действия. Затем вам будет предложено ввести такие вещи, как «Название страны», но вы можете просто нажать Enter и принять значения по умолчанию.

Добавьте -subj '/CN=localhost', чтобы скрыть вопросы о содержимом сертификата (замените localhost на желаемый домен).

Самозаверяющие сертификаты не проверяются третьими сторонами, если вы предварительно не импортируете их в браузеры. Если вам нужна дополнительная безопасность, вы должны использовать сертификат, подписанный центром сертификации (CA).

openssl позволяет сгенерировать самоподписанный сертификат с помощью одной команды (-newkey дает указание сгенерировать закрытый ключ, а -x509 дает указание выдать самоподписанный сертификат вместо запроса на подпись) ::

openssl req -x509 -newkey rsa:4096 
-keyout my.key -passout pass:123456 -out my.crt 
-days 365 
-subj /CN=localhost/O=home/C=US/emailAddress=me@mail.internal 
-addext "subjectAltName = DNS:localhost,DNS:web.internal,email:me@mail.internal" 
-addext keyUsage=digitalSignature -addext extendedKeyUsage=serverAuth

Вы можете сгенерировать закрытый ключ и создать самозаверяющий сертификат в отдельные шаги:

openssl genrsa -out my.key -passout pass:123456 2048

openssl req -x509 
-key my.key -passin pass:123456 -out my.csr 
-days 3650 
-subj /CN=localhost/O=home/C=US/emailAddress=me@mail.internal 
-addext "subjectAltName = DNS:localhost,DNS:web.internal,email:me@mail.internal" 
-addext keyUsage=digitalSignature -addext extendedKeyUsage=serverAuth

Просмотрите полученный сертификат:

openssl x509 -text -noout -in my.crt

Java keytool создает хранилище PKCS # 12 ::

keytool -genkeypair -keystore my.p12 -alias master 
-storetype pkcs12 -keyalg RSA -keysize 2048 -validity 3650 
-storepass 123456 
-dname "CN=localhost,O=home,C=US" 
-ext 'san=dns:localhost,dns:web.internal,email:me@mail.internal'

Чтобы экспортировать самоподписанный сертификат:

keytool -exportcert -keystore my.p12 -file my.crt 
-alias master -rfc -storepass 123456

Просмотрите полученный сертификат:

keytool -printcert -file my.crt

certtool из GnuTLS не позволяет передавать различные атрибуты из CLI. Не люблю возиться с конфигурационными файлами ((

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

Основная причина, по которой никто не хочет получать подписанный сертификат от центра сертификации, – это стоимость – Symantec плата от $ 995 -! $ 1 999 в год за сертификаты – только для сертификата, предназначенный для внутренней сети, Symantec взимает 399 долларов США в год. Эту стоимость легко оправдать, если вы обрабатываете платежи по кредитной карте или работаете в центре прибыли высокоприбыльной компании. Это больше, чем многие могут себе позволить для личного проекта, который создается в Интернете, или для некоммерческой организации, работающей с минимальным бюджетом, или если кто-то работает в центре затрат организации – центры затрат всегда стараются сделать больше менее.

Альтернативой является использование certbot (см. о certbot ). Certbot – это простой в использовании автоматический клиент, который извлекает и развертывает сертификаты SSL / TLS для вашего веб-сервера.

Если вы настроили certbot, вы можете разрешить ему создавать и поддерживать сертификат, выданный центром сертификации Let’s Encrypt.

Я сделал это на выходных для своей организации. Я установил необходимые пакеты для certbot на свой сервер (Ubuntu 16.04), а затем выполнил команду, необходимую для установки и включения certbot. Вероятно, понадобится плагин DNS для certbot – в настоящее время мы используем < a href = “https://certbot-dns-digitalocean.readthedocs.io/en/stable/” rel = “nofollow noreferrer”> DigitalOcean , хотя может скоро перейти на другую службу.

Обратите внимание, что некоторые инструкции были не совсем правильными, и потребовалось немного времени и времени на выяснение у Google. В первый раз это заняло у меня изрядное количество времени, но теперь я думаю, что смогу сделать это за считанные минуты.

Что касается DigitalOcean, я столкнулся с проблемой, когда мне было предложено ввести путь к вашему INI-файлу учетных данных DigitalOcean. Сценарий имеет в виду страницу Приложения и API и вкладку Токены / Ключ. на этой странице. Вам необходимо иметь или сгенерировать личный токен доступа (чтение и запись) для API DigitalOcean – это шестнадцатеричная строка из 65 символов. Затем эту строку необходимо поместить в файл на веб-сервере, с которого вы запускаете certbot. В первой строке этого файла может быть комментарий (комментарии начинаются с символа #). Вторая строка:

dns_digitalocean_token = 0000111122223333444455556666777788889999aaaabbbbccccddddeeeeffff

Как только я понял, как настроить токен чтения и записи для API DigitalOcean, было довольно просто использовать certbot для настройки шаблонный сертификат. Обратите внимание, что не нужно настраивать подстановочный сертификат, вместо этого можно указать каждый домен и поддомен, к которым нужно применять сертификат. Это был шаблонный сертификат, для которого требовался INI-файл учетных данных, содержащий токен личного доступа от DigitalOcean.

Обратите внимание, что сертификаты открытого ключа (также известные как сертификаты идентичности или сертификаты SSL) истекают и требуют обновления. Таким образом, вам нужно будет периодически (повторно) продлевать свой сертификат. Документация по certbot охватывает продление сертификатов.

Я планирую написать сценарий, который будет использовать команду openssl для получения даты истечения срока действия моего сертификата и для запуска обновления, если до истечения срока его действия осталось 30 дней или меньше. Затем я добавлю этот скрипт в cron и буду запускать его раз в день.

Вот команда для чтения даты истечения срока действия вашего сертификата:

root@prod-host:~# /usr/bin/openssl x509 -enddate -noout -in path-to-certificate-pem-file
notAfter=May 25 19:24:12 2021 GMT

Сгенерировать ключи

Я использую /etc/mysql для хранения сертификатов, потому что /etc/apparmor.d/usr.sbin.mysqld содержит /etc/mysql/*.pem r.

sudo su -
cd /etc/mysql
openssl genrsa -out ca-key.pem 2048;
openssl req -new -x509 -nodes -days 1000 -key ca-key.pem -out ca-cert.pem;
openssl req -newkey rsa:2048 -days 1000 -nodes -keyout server-key.pem -out server-req.pem;
openssl x509 -req -in server-req.pem -days 1000 -CA ca-cert.pem -CAkey ca-key.pem -set_serial 01 -out server-cert.pem;
openssl req -newkey rsa:2048 -days 1000 -nodes -keyout client-key.pem -out client-req.pem;
openssl x509 -req -in client-req.pem -days 1000 -CA ca-cert.pem -CAkey ca-key.pem -set_serial 01 -out client-cert.pem;

Добавить конфигурацию

/etc/mysql/my.cnf

[client]
ssl-ca=/etc/mysql/ca-cert.pem
ssl-cert=/etc/mysql/client-cert.pem
ssl-key=/etc/mysql/client-key.pem

[mysqld]
ssl-ca=/etc/mysql/ca-cert.pem
ssl-cert=/etc/mysql/server-cert.pem
ssl-key=/etc/mysql/server-key.pem

Про сертификаты:  Сертификат соответствия С-US.ПБ25.В.04578 | Система противопожарной сигнализации «SIMPLEX TIME RECORDER CO.»

В моей настройке сервер Ubuntu вошел в систему: /var/log/mysql/error.log

  • SSL error: Unable to get certificate from '...'

    MySQL может быть запрещен доступ для чтения к вашему файлу сертификата, если он не находится в конфигурации apparmors / а>. Как упоминалось в предыдущих шагах ^, сохраните все наши сертификаты как файлы .pem в каталоге /etc/mysql/, который по умолчанию одобрен apparmor (или измените свой apparmor / SELinux, чтобы разрешить доступ к тому месту, где вы их сохранили. )

  • SSL error: Unable to get private key

    Ваша версия сервера MySQL может не поддерживать формат rsa:2048 по умолчанию

    Преобразуйте сгенерированный rsa:2048 в простой rsa с помощью:

    openssl rsa -in server-key.pem -out server-key.pem
    openssl rsa -in client-key.pem -out client-key.pem
    
  • Проверьте, поддерживает ли локальный сервер SSL

     mysql -u root -p  mysql> показать такие переменные, как "% ssl%";    ---------------   ----------------------------    |  Имя_переменной |  Значение |    ---------------   ----------------------------    |  have_openssl |  ДА |  |  have_ssl |  ДА |  |  ssl_ca |  /etc/mysql/ca-cert.pem |  |  ssl_capath |  |  |  ssl_cert |  /etc/mysql/server-cert.pem |  |  ssl_cipher |  |  |  ssl_key |  /etc/mysql/server-key.pem |    ---------------   ----------------------------    

  • Проверка того, что соединение с базой данных зашифровано SSL:

    Проверка соединения

    При входе в экземпляр MySQL вы можете выполнить запрос:

     отображать статус типа «Ssl_cipher»;  

    Если ваше соединение не зашифровано, результат будет пустым:

     mysql> показывает статус как 'Ssl_cipher';    ---------------   -------    |  Имя_переменной |  Значение |    ---------------   -------    |  Ssl_cipher |  |    ---------------   -------    1 ряд в комплекте (0,00 сек)  

    В противном случае для используемого шифра будет показана строка ненулевой длины:

     mysql> показывает статус как 'Ssl_cipher';    ---------------   --------------------    |  Имя_переменной |  Значение |    ---------------   --------------------    |  Ssl_cipher |  DHE-RSA-AES256-SHA |    ---------------   --------------------    1 ряд в комплекте (0,00 сек)  

  • Требовать ssl для подключения определенного пользователя (‘require ssl’) :

    Указывает серверу разрешать для учетной записи только SSL-шифрованные соединения.

     ПРЕДОСТАВЛЯТЬ ВСЕ ПРИВИЛЕГИИ НА test. * 'root' @ 'localhost'    ТРЕБУЕТСЯ SSL;  

    Для подключения клиент должен указать параметр –ssl-ca для аутентификации сертификата сервера и может дополнительно указать параметры –ssl-key и –ssl-cert. Если ни опция –ssl-ca, ни опция –ssl-capath не указаны, клиент не аутентифицирует сертификат сервера.


Альтернативная ссылка: подробное руководство по Безопасное соединение PHP с MySQL с помощью SSL.

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

Итак, шаг за шагом. Создайте файл config_ssl_ca.cnf Обратите внимание, что в файле конфигурации есть опция basicConstraints = CA: true , что означает, что этот сертификат должен быть корневым.

Это хорошая практика, потому что вы создаете его один раз и можете использовать повторно.

[ req ]
default_bits = 2048

prompt = no
distinguished_name=req_distinguished_name
req_extensions = v3_req

[ req_distinguished_name ]
countryName=UA
stateOrProvinceName=root region
localityName=root city
organizationName=Market(localhost)
organizationalUnitName=roote department
commonName=market.localhost
emailAddress=root_email@root.localhost

[ alternate_names ]
DNS.1        = market.localhost
DNS.2        = www.market.localhost
DNS.3        = mail.market.localhost
DNS.4        = ftp.market.localhost
DNS.5        = *.market.localhost

[ v3_req ]
keyUsage=digitalSignature
basicConstraints=CA:true
subjectKeyIdentifier = hash
subjectAltName = @alternate_names

Следующий файл конфигурации для вашего дочернего сертификата будет называться config_ssl.cnf .

[ req ]
default_bits = 2048

prompt = no
distinguished_name=req_distinguished_name
req_extensions = v3_req

[ req_distinguished_name ]
countryName=UA
stateOrProvinceName=Kyiv region
localityName=Kyiv
organizationName=market place
organizationalUnitName=market place department
commonName=market.localhost
emailAddress=email@market.localhost

[ alternate_names ]
DNS.1        = market.localhost
DNS.2        = www.market.localhost
DNS.3        = mail.market.localhost
DNS.4        = ftp.market.localhost
DNS.5        = *.market.localhost

[ v3_req ]
keyUsage=digitalSignature
basicConstraints=CA:false
subjectAltName = @alternate_names
subjectKeyIdentifier = hash

Первый шаг – создать Root-ключ и сертификат

openssl genrsa -out ca.key 2048
openssl req -new -x509 -key ca.key -out ca.crt -days 365 -config config_ssl_ca.cnf

На втором этапе создается дочерний ключ и файл CSR – Certificate Signing Request. Потому что идея заключается в том, чтобы подписать дочерний сертификат root и получить правильный сертификат.

openssl genrsa -out market.key 2048
openssl req -new -sha256 -key market.key -config config_ssl.cnf -out market.csr

Откройте терминал Linux и выполните эту команду

echo 00 > ca.srl
touch index.txt

Текстовый файл ca.srl , содержащий следующий серийный номер в шестнадцатеричном формате. Обязательный. Этот файл должен присутствовать и содержать действительный серийный номер.

На последнем этапе создайте еще один файл конфигурации и назовите его config_ca.cnf .

# we use 'ca' as the default section because we're usign the ca command
[ ca ]
default_ca = my_ca

[ my_ca ]
#  a text file containing the next serial number to use in hex. Mandatory.
#  This file must be present and contain a valid serial number.
serial = ./ca.srl

# the text database file to use. Mandatory. This file must be present though
# initially it will be empty.
database = ./index.txt

# specifies the directory where new certificates will be placed. Mandatory.
new_certs_dir = ./

# the file containing the CA certificate. Mandatory
certificate = ./ca.crt

# the file contaning the CA private key. Mandatory
private_key = ./ca.key

# the message digest algorithm. Remember to not use MD5
default_md = sha256

# for how many days will the signed certificate be valid
default_days = 365

# a section with a set of variables corresponding to DN fields
policy = my_policy

# MOST IMPORTANT PART OF THIS CONFIG
copy_extensions = copy

[ my_policy ]
# if the value is "match" then the field value must match the same field in the
# CA certificate. If the value is "supplied" then it must be present.
# Optional means it may be present. Any fields not mentioned are silently
# deleted.
countryName = match
stateOrProvinceName = supplied
organizationName = supplied
commonName = market.localhost
organizationalUnitName = optional
commonName = supplied

Вы спросите, почему так сложно, зачем нужно создавать еще один конфиг для подписи дочернего сертификата root. Ответ прост, потому что в дочернем сертификате должен быть блок SAN – альтернативные имена субъектов. Если мы подпишем дочерний сертификат с помощью утилит «openssl x509», корневой сертификат удалит поле SAN в дочернем сертификате. Поэтому мы используем openssl ca вместо openssl x509, чтобы избежать удаления поля SAN. Мы создаем новый файл конфигурации и приказываем ему скопировать все расширенные поля copy_extensions = copy .

openssl ca -config config_ca.cnf -out market.crt -in market.csr

Программа задает вам 2 вопроса:

  1. Подпишите сертификат? Скажите “Y”
  2. 1 из 1 запросов на сертификат подтвержден, совершить? Скажите “Y”

В терминале вы видите предложение со словом «База данных», это означает файл index.txt, который вы создаете командой «touch». Он будет содержать всю информацию обо всех сертификатах, которые вы создаете с помощью утилиты “openssl ca”. Чтобы проверить действительность сертификата, используйте:

openssl rsa -in market.key -check

Если вы хотите посмотреть, что внутри CRT:

openssl x509 -in market.crt -text -noout

Если вы хотите посмотреть, что внутри в CSR:

openssl req -in market.csr -noout -text 

Это сценарий, который я использую в локальных ящиках для установки SAN (subjectAltName) в самозаверяющих сертификатах.

Этот сценарий берет имя домена (example.com) и генерирует SAN для * .example.com и example.com в одном сертификате. В следующих разделах есть комментарии. Назовите сценарий (например, generate-ssl.sh) и дайте ему права на выполнение. Файлы будут записаны в тот же каталог, что и сценарий.

Chrome 58 и более поздних версий требует, чтобы SAN был установлен в самозаверяющих сертификатах.

#!/usr/bin/env bash

# Set the TLD domain we want to use
BASE_DOMAIN="example.com"

# Days for the cert to live
DAYS=1095

# A blank passphrase
PASSPHRASE=""

# Generated configuration file
CONFIG_FILE="config.txt"

cat > $CONFIG_FILE <<-EOF
[req]
default_bits = 2048
prompt = no
default_md = sha256
x509_extensions = v3_req
distinguished_name = dn

[dn]
C = CA
ST = BC
L = Vancouver
O = Example Corp
OU = Testing Domain
emailAddress = webmaster@$BASE_DOMAIN
CN = $BASE_DOMAIN

[v3_req]
subjectAltName = @alt_names

[alt_names]
DNS.1 = *.$BASE_DOMAIN
DNS.2 = $BASE_DOMAIN
EOF

# The file name can be anything
FILE_NAME="$BASE_DOMAIN"

# Remove previous keys
echo "Removing existing certs like $FILE_NAME.*"
chmod 770 $FILE_NAME.*
rm $FILE_NAME.*

echo "Generating certs for $BASE_DOMAIN"

# Generate our Private Key, CSR and Certificate
# Use SHA-2 as SHA-1 is unsupported from Jan 1, 2021

openssl req -new -x509 -newkey rsa:2048 -sha256 -nodes -keyout "$FILE_NAME.key" -days $DAYS -out "$FILE_NAME.crt" -passin pass:$PASSPHRASE -config "$CONFIG_FILE"

# OPTIONAL - write an info to see the details of the generated crt
openssl x509 -noout -fingerprint -text < "$FILE_NAME.crt" > "$FILE_NAME.info"

# Protect the key
chmod 400 "$FILE_NAME.key"

Этот сценарий также записывает информационный файл, чтобы вы могли проверить новый сертификат и убедиться, что SAN настроен правильно.

                ...
                28:dd:b8:1e:34:b5:b1:44:1a:60:6d:e3:3c:5a:c4:
                da:3d
            Exponent: 65537 (0x10001)
    X509v3 extensions:
        X509v3 Subject Alternative Name: 
            DNS:*.example.com, DNS:example.com
Signature Algorithm: sha256WithRSAEncryption
     3b:35:5a:d6:9e:92:4f:fc:f4:f4:87:78:cd:c7:8d:cd:8c:cc:
     ...

Если вы используете Apache, вы можете ссылаться на вышеуказанный сертификат в своем файле конфигурации следующим образом:

<VirtualHost _default_:443>
    ServerName example.com
    ServerAlias www.example.com
    DocumentRoot /var/www/htdocs

    SSLEngine on
    SSLCertificateFile path/to/your/example.com.crt
    SSLCertificateKeyFile path/to/your/example.com.key
</VirtualHost>

Не забудьте перезапустить сервер Apache (или Nginx, или IIS), чтобы новый сертификат вступил в силу.

Начиная с 2021 года с OpenSSL ≥ 1.1.1, следующая команда обслуживает все ваши потребности, включая SAN:

openssl req -x509 -newkey rsa:4096 -sha256 -days 3650 -nodes 
  -keyout example.key -out example.crt -subj "/CN=example.com" 
  -addext "subjectAltName=DNS:example.com,DNS:www.example.net,IP:10.0.0.1"

В старых системах с OpenSSL ≤ 1.1.0, таких как Debian ≤ 9 или CentOS ≤ 7, необходимо использовать более длинную версию этой команды:

openssl req -x509 -newkey rsa:4096 -sha256 -days 3650 -nodes 
  -keyout example.key -out example.crt -extensions san -config 
  <(echo "[req]"; 
    echo distinguished_name=req; 
    echo "[san]"; 
    echo subjectAltName=DNS:example.com,DNS:www.example.net,IP:10.0.0.1
    ) 
  -subj "/CN=example.com"

Любая команда создает сертификат, который

Создаются следующие файлы:

  • Закрытый ключ: example.key
  • Сертификат: example.crt

Вся информация предоставляется в командной строке. Здесь нет интерактивного ввода , который вас раздражает. Нет файлов конфигурации , с которыми вам нужно возиться. Все необходимые шаги выполняются с помощью однократного вызова OpenSSL : от генерации закрытого ключа до самозаверяющего сертификата.

Замечание №1: параметры шифрования

Поскольку сертификат является самоподписанным и должен быть принят пользователями вручную, нет смысла использовать короткий срок действия или слабую криптографию.

В будущем вы, возможно, захотите использовать более 4096 бит для ключа RSA и алгоритм хеширования, более сильный, чем sha256, но с 2021 года это нормальные значения. Они достаточно сильны и поддерживаются всеми современными браузерами.

Замечание №2: параметр “-nodes

Теоретически вы можете не указывать параметр -nodes (что означает «без шифрования DES»), и в этом случае example.key будет зашифрован паролем. Однако это почти никогда не бывает полезно для установки на сервере, потому что вам придется либо сохранить пароль на сервере, либо вам придется вводить его вручную при каждой перезагрузке.

Замечание №3: см. также

Я что-то пропустил? Это правильный способ создания самозаверяющего сертификата?

Самозаверяющий сертификат легко создать. Вы просто используете команду openssl req. Может быть сложно создать такой, который будет использоваться большинством клиентов, таких как браузеры и инструменты командной строки.

Это сложно, потому что у браузеров есть собственный набор требований, и они более строгие, чем IETF. Требования, используемые браузерами, задокументированы на форумах CA / браузеров (см. Ссылки ниже). Ограничения возникают в двух ключевых областях: (1) якоря доверия и (2) имена DNS.

Современные браузеры (например, варез, который мы используем в 2021/2021 гг.) Хотят получить сертификат, который связан с якорем доверия, и они хотят, чтобы имена DNS были представлены в сертификате определенным образом. И браузеры активно выступают против самозаверяющих сертификатов серверов.

Некоторые браузеры не совсем упрощают импорт самозаверяющего сертификата сервера. Фактически, вы не можете этого сделать с некоторыми браузерами, такими как браузер Android. Итак, полное решение – стать вашим собственным авторитетом.

Если вы не становитесь вашим авторитетом, вы должны правильно указать DNS-имена, чтобы дать сертификату наибольшие шансы на успех. Но я бы посоветовал вам стать вашим собственным авторитетом. Легко стать своим авторитетом, и это позволит избежать всех проблем с доверием (кому лучше доверять, чем себе?).


Вероятно, это не тот сайт, который вы ищете!
Сертификату безопасности сайта не доверяют!

Это связано с тем, что браузеры используют предопределенный список якорей доверия для проверки сертификатов сервера. Самозаверяющий сертификат не связан с доверенным якорем.

Лучший способ избежать этого:

  1. Создайте свой собственный авторитет (т. Е. Станьте CA)
  2. Создайте запрос на подпись сертификата (CSR) для сервера
  3. Подпишите CSR сервера своим ключом CA
  4. Установите сертификат сервера на сервер
  5. Установите сертификат CA на клиенте

Шаг 1 – Создать собственный центр означает просто создать самозаверяющий сертификат с CA: true и правильным использованием ключа. Это означает, что Subject и Issuer – это одна и та же сущность, CA имеет значение true в Basic Constraints (он также должен быть отмечен как критический), использование ключа: keyCertSign и crlSign (если вы используете CRL), а Subject Key Identifier (SKI) совпадает с Authority Key Identifier (AKI).

Чтобы стать вашим собственным центром сертификации, см. * Как подписать запрос на подпись сертификата в центре сертификации? на Stack Overflow. Затем импортируйте свой ЦС в хранилище доверия, используемое браузером.

Шаги 2–4 примерно соответствуют тому, что вы делаете сейчас для общедоступного сервера, когда подключаете услуги центра сертификации, например Startcom или CAcert. Шаги 1 и 5 позволяют избежать стороннего авторитета и действовать как собственный авторитет (кому лучше доверять, чем себе?).

Следующий лучший способ избежать предупреждения браузера – доверять сертификату сервера. Но некоторые браузеры, например браузер Android по умолчанию, не позволяют вам этого делать. Так что на платформе это никогда не сработает.

Проблема того, что браузеры (и другие подобные пользовательские агенты) не доверяют самозаверяющим сертификатам, станет большой проблемой в Интернете вещей (IoT). Например, что произойдет, если вы подключите термостат или холодильник, чтобы запрограммировать его? Ответ: ничего хорошего с точки зрения пользовательского опыта.

Рабочая группа W3C по WebAppSec начинает изучать эту проблему. См., Например, Предложение: Пометка HTTP как небезопасного


Как создать самоподписанный сертификат с OpenSSL

Приведенные ниже команды и файл конфигурации создают самозаверяющий сертификат (он также показывает, как создать запрос на подпись). Они отличаются от других ответов в одном отношении: DNS-имена, используемые для самоподписанного сертификата, указаны в Subject Alternate Name (SAN) , а не в Common Name (CN) .

Имена DNS помещаются в SAN через файл конфигурации со строкой subjectAltName = @alternate_names (нет возможности сделать это через командную строку). Затем в файле конфигурации есть раздел alternate_names (вы должны настроить его по своему вкусу):

[ alternate_names ]

DNS.1       = example.com
DNS.2       = www.example.com
DNS.3       = mail.example.com
DNS.4       = ftp.example.com

# Add these if you need them. But usually you don't want them or
#   need them in production. You may need them for development.
# DNS.5       = localhost
# DNS.6       = localhost.localdomain
# IP.1        = 127.0.0.1
# IP.2        = ::1

Важно указать DNS-имя в SAN, а не в CN, потому что оба и IETF, и CA / форумы браузеров определяют эту практику. Они также указывают, что имена DNS в CN устарели (но не запрещены). Если указать DNS-имя в CN, оно должно быть включено в SAN в соответствии с политиками CA / B. Таким образом, вы не можете избежать использования альтернативного имени субъекта.

Если вы не поместите DNS-имена в SAN, тогда сертификат не сможет пройти проверку в браузере и других пользовательских агентах, которые следуют рекомендациям CA / Browser Forum.

Связано: браузеры следуют политикам CA / Browser Forum; а не политики IETF. Это одна из причин, по которой сертификат, созданный с помощью OpenSSL (который обычно соответствует IETF), иногда не проверяется в браузере (браузеры следуют CA / B). Это разные стандарты, у них разные политики выпуска и разные требования к валидации.


Создайте самоподписанный сертификат (обратите внимание на добавленную опцию -x509):

openssl req -config example-com.conf -new -x509 -sha256 -newkey rsa:2048 -nodes 
    -keyout example-com.key.pem -days 365 -out example-com.cert.pem

Создайте запрос на подпись (обратите внимание на отсутствие опции -x509):

openssl req -config example-com.conf -new -sha256 -newkey rsa:2048 -nodes 
    -keyout example-com.key.pem -days 365 -out example-com.req.pem

Распечатайте самозаверяющий сертификат :

openssl x509 -in example-com.cert.pem -text -noout

Распечатайте запрос на подпись :

openssl req -in example-com.req.pem -text -noout

Файл конфигурации (передается с помощью параметра -config)

[ req ]
default_bits        = 2048
default_keyfile     = server-key.pem
distinguished_name  = subject
req_extensions      = req_ext
x509_extensions     = x509_ext
string_mask         = utf8only

# The Subject DN can be formed using X501 or RFC 4514 (see RFC 4519 for a description).
#   Its sort of a mashup. For example, RFC 4514 does not provide emailAddress.
[ subject ]
countryName         = Country Name (2 letter code)
countryName_default     = US

stateOrProvinceName     = State or Province Name (full name)
stateOrProvinceName_default = NY

localityName            = Locality Name (eg, city)
localityName_default        = New York

organizationName         = Organization Name (eg, company)
organizationName_default    = Example, LLC

# Use a friendly name here because it's presented to the user. The server's DNS
#   names are placed in Subject Alternate Names. Plus, DNS names here is deprecated
#   by both IETF and CA/Browser Forums. If you place a DNS name here, then you
#   must include the DNS name in the SAN too (otherwise, Chrome and others that
#   strictly follow the CA/Browser Baseline Requirements will fail).
commonName          = Common Name (e.g. server FQDN or YOUR name)
commonName_default      = Example Company

emailAddress            = Email Address
emailAddress_default        = test@example.com

# Section x509_ext is used when generating a self-signed certificate. I.e., openssl req -x509 ...
[ x509_ext ]

subjectKeyIdentifier        = hash
authorityKeyIdentifier    = keyid,issuer

# You only need digitalSignature below. *If* you don't allow
#   RSA Key transport (i.e., you use ephemeral cipher suites), then
#   omit keyEncipherment because that's key transport.
basicConstraints        = CA:FALSE
keyUsage            = digitalSignature, keyEncipherment
subjectAltName          = @alternate_names
nsComment           = "OpenSSL Generated Certificate"

# RFC 5280, Section 4.2.1.12 makes EKU optional
#   CA/Browser Baseline Requirements, Appendix (B)(3)(G) makes me confused
#   In either case, you probably only need serverAuth.
# extendedKeyUsage    = serverAuth, clientAuth

# Section req_ext is used when generating a certificate signing request. I.e., openssl req ...
[ req_ext ]

subjectKeyIdentifier        = hash

basicConstraints        = CA:FALSE
keyUsage            = digitalSignature, keyEncipherment
subjectAltName          = @alternate_names
nsComment           = "OpenSSL Generated Certificate"

# RFC 5280, Section 4.2.1.12 makes EKU optional
#   CA/Browser Baseline Requirements, Appendix (B)(3)(G) makes me confused
#   In either case, you probably only need serverAuth.
# extendedKeyUsage    = serverAuth, clientAuth

[ alternate_names ]

DNS.1       = example.com
DNS.2       = www.example.com
DNS.3       = mail.example.com
DNS.4       = ftp.example.com

# Add these if you need them. But usually you don't want them or
#   need them in production. You may need them for development.
# DNS.5       = localhost
# DNS.6       = localhost.localdomain
# DNS.7       = 127.0.0.1

# IPv6 localhost
# DNS.8     = ::1

Возможно, вам потребуется сделать следующее для Chrome. В противном случае Chrome может пожаловаться на Общее имя недействительно (ERR_CERT_COMMON_NAME_INVALID). Я не уверен, какова связь между IP-адресом в SAN и CN в этом случае.

# IPv4 localhost
# IP.1       = 127.0.0.1

# IPv6 localhost
# IP.2     = ::1

Существуют и другие правила, касающиеся обработки имен DNS в сертификатах X.509 / PKIX. Обратитесь к этим документам, чтобы узнать правила:

RFC 6797 и RFC 7469 перечислены, потому что они более строгие, чем другие документы RFC и CA / B. RFC 6797 и 7469 не также разрешают IP-адрес.

Оцените статью
Мой сертификат
Добавить комментарий