Сообщение об ошибке
400 No required SSL certificate was sent
Также выводится как
- client sent no required SSL certificate while reading client request headers
Заголовок страницы — «400 No required SSL certificate was sent»; если сертификат не проходит проверку, nginx показывает вместо этого «400 The SSL certificate error». Строка в журнале пишется с уровнем info, поэтому при уровне error_log по умолчанию её не видно.
nginx — ssl_verify_client on, request without a client certificate
Что это означает
В nginx включена взаимная TLS-аутентификация (ssl_verify_client on), а запрос пришёл по TLS-соединению, в котором клиент не предъявил сертификат. nginx не обрывает рукопожатие, а завершает его и отвечает на каждый запрос этой страницей HTTP 400, записывая в журнал «client sent no required SSL certificate» с уровнем info. Исправлять нужно на клиенте: он должен предъявить сертификат, выпущенный CA, указанным в ssl_client_certificate.
Почему это происходит
Клиент не отправил сертификат
частоcurl, скрипты и API-клиенты без --cert/--key или аналогичного параметра библиотеки; контейнеры или задания CI, у которых нет секрета с сертификатом.
В браузере нет подходящего сертификата
частоБраузеры предлагают только сертификаты, выпущенные теми CA, о которых сообщает nginx (их список берётся из ssl_client_certificate); если сертификат выпущен другим CA или вообще не импортирован, браузер ничего не отправляет.
TLS терминируется на прокси перед nginx
иногдаCDN, балансировщик нагрузки или ещё один nginx перед ним открывает собственное TLS-соединение без клиентского сертификата; тогда взаимную TLS-аутентификацию нужно настраивать на этом участке (или выполнять на периметре).
Как исправить
- 1.
Предъявите клиентский сертификат
Передайте клиенту сертификат и ключ; для браузеров и хранилищ ключей Windows/macOS соберите их в пакет PKCS#12 и импортируйте файл.
bash curl --cert client.pem --key client.key https://mtls.example.com/ # Browsers: import the client certificate with its key as PKCS#12 openssl pkcs12 -export -in client.pem -inkey client.key -out client.p12 - 2.
Проксирование к сервису с mTLS: настройте сертификат для проксируемого сервера
Когда клиентом сервиса с mTLS выступает сам nginx, сертификат для соединения с проксируемым сервером задают proxy_ssl_certificate и proxy_ssl_certificate_key.
text # nginx proxying to an mTLS upstream: present the client certificate on the upstream connection location / { proxy_pass https://mtls.example.com; proxy_ssl_certificate /etc/nginx/tls/client.pem; proxy_ssl_certificate_key /etc/nginx/tls/client.key; proxy_ssl_server_name on; } - 3.
Требуйте сертификаты только там, где они нужны
ssl_verify_client optional вместе с проверкой $ssl_client_verify в каждом location оставляет проверки состояния и публичные пути доступными без сертификата.
text # Require the certificate only where needed ssl_verify_client optional; location /api/ { if ($ssl_client_verify != SUCCESS) { return 403; } }