Chrome 58에서 작동하는 openssl을 사용하여 자체 서명 된 인증서 생성


52

크롬 58으로 더 이상에 의존 자체 서명 인증서 표시지지 않습니다 Common Name: https://productforums.google.com/forum/#!topic/chrome/zVo3M8CgKzQ;context-place=topicsearchin/chrome/category $ 3ACanary % 7Csort를 : 관련성 : 7

대신을 사용해야합니다 Subject Alt Name. : 나는 이전에 자체 서명 인증서를 생성하는 방법에 대한이 가이드 다음 한 https://devcenter.heroku.com/articles/ssl-certificate-self 내가 필요한 때문에 큰 일을 server.crt하고 server.key내가 뭘하는지에 대한 파일을. 이제 SANChrome 58에서 작동하지 않는 모든 시도 가 포함 된 새 인증서를 생성해야합니다 .

다음은 내가 한 일입니다.

위에서 언급 한 Heroku 기사의 단계에 따라 키를 생성했습니다. 그런 다음 새로운 OpenSSL 구성 파일을 작성했습니다.

[ req ]
default_bits        = 2048
distinguished_name  = req_distinguished_name
req_extensions      = san
extensions          = san
[ req_distinguished_name ]
countryName         = US
stateOrProvinceName = Massachusetts
localityName        = Boston
organizationName    = MyCompany
[ san ]
subjectAltName      = DNS:dev.mycompany.com

그런 server.crt다음 다음 명령으로를 생성했습니다 .

openssl req \
-new \
-key server.key \
-out server.csr \
-config config.cnf \
-sha256 \
-days 3650

Mac을 사용하고 있으므로 server.crt키 체인으로 파일을 열고 시스템 인증서에 추가했습니다. 그런 다음로 설정했습니다 Always Trust.

SAN 값을 설정하기위한 구성 파일을 제외하고 이들은 이전 버전의 Chrome에서 자체 서명 인증서를 생성하고 신뢰하는 데 사용한 단계와 비슷한 단계입니다.

그러나이 후에도 여전히 ERR_CERT_COMMON_NAME_INVALIDChrome 58을 얻습니다 .

답변:


61

내 해결책 :

openssl req \
    -newkey rsa:2048 \
    -x509 \
    -nodes \
    -keyout server.key \
    -new \
    -out server.crt \
    -subj /CN=dev.mycompany.com \
    -reqexts SAN \
    -extensions SAN \
    -config <(cat /System/Library/OpenSSL/openssl.cnf \
        <(printf '[SAN]\nsubjectAltName=DNS:dev.mycompany.com')) \
    -sha256 \
    -days 3650

상태 : 나를 위해 작동


2
서브 쉘을 많이 사용합니다. 나는 당신이 그것을 조금 단순화 할 수 있다고 생각합니다 :-config <(cat /System/Library/OpenSSL/openssl.cnf ; printf '[SAN]\nsubjectAltName=DNS:dev.mycompany.com')
jrwren

1
더 이상 Subject Alt Name 오류가 발생하지 않지만 이제는 일반 이름에 대한 오류가 발생하고 다운로드 한 인증서를 "항상 신뢰"로 설정해도 작동하지 않습니다. 이견있는 사람? @bcardarella
rugbert

2
Chrome 59로 업데이트하면 인증서에 다음과 같은 오류가 표시됩니다. 사이트의 인증서 체인 (net :: ERR_CERT_COMMON_NAME_INVALID)에 문제가 있습니다.
theHarsh

1
나는 변경 dev.company.namelocalhost이것은 로컬 호스트에서 지역 개발 사이트를 봉사했다. macOS에서는 키 체인에 인증서를 추가하고 SSL을 "항상 신뢰"로 설정해야했습니다.
Daniel M.

1
그것은 지금까지 가장 간단한 해결책이며 sslconf로 나사를 조이거나 CA를 설치할 필요가 없습니다.
bp.

16

Windows에서는이 스크립트를 SSL 폴더에 makeCERT.bat로 저장하십시오. example.cnf, example.crt, example.key 파일이 생성됩니다.

@echo off

REM IN YOUR SSL FOLDER, SAVE THIS FILE AS: makeCERT.bat
REM AT COMMAND LINE IN YOUR SSL FOLDER, RUN: makecert
REM IT WILL CREATE THESE FILES: example.cnf, example.crt, example.key
REM IMPORT THE .crt FILE INTO CHROME Trusted Root Certification Authorities
REM REMEMBER TO RESTART APACHE OR NGINX AFTER YOU CONFIGURE FOR THESE FILES

REM PLEASE UPDATE THE FOLLOWING VARIABLES FOR YOUR NEEDS.
SET HOSTNAME=example
SET DOT=com
SET COUNTRY=US
SET STATE=KS
SET CITY=Olathe
SET ORGANIZATION=IT
SET ORGANIZATION_UNIT=IT Department
SET EMAIL=webmaster@%HOSTNAME%.%DOT%

(
echo [req]
echo default_bits = 2048
echo prompt = no
echo default_md = sha256
echo x509_extensions = v3_req
echo distinguished_name = dn
echo:
echo [dn]
echo C = %COUNTRY%
echo ST = %STATE%
echo L = %CITY%
echo O = %ORGANIZATION%
echo OU = %ORGANIZATION_UNIT%
echo emailAddress = %EMAIL%
echo CN = %HOSTNAME%.%DOT%
echo:
echo [v3_req]
echo subjectAltName = @alt_names
echo:
echo [alt_names]
echo DNS.1 = *.%HOSTNAME%.%DOT%
echo DNS.2 = %HOSTNAME%.%DOT%
)>%HOSTNAME%.cnf

openssl req -new -x509 -newkey rsa:2048 -sha256 -nodes -keyout %HOSTNAME%.key -days 3560 -out %HOSTNAME%.crt -config %HOSTNAME%.cnf

13

나를 위해 일하는 해결책은 다음과 같습니다.

CA 키 및 인증서 생성

# openssl genrsa -out server_rootCA.key 2048
# openssl req -x509 -new -nodes -key server_rootCA.key -sha256 -days 3650 -out server_rootCA.pem

server_rootCA.csr.cnf 작성

# server_rootCA.csr.cnf
[req]
default_bits = 2048
prompt = no
default_md = sha256
distinguished_name = dn

[dn]
C=DE
ST=Berlin
L=NeuKoelln
O=Weisestrasse
OU=local_RootCA
emailAddress=ikke@server.berlin
CN = server.berlin

v3.ext 구성 파일 작성

# v3.ext
authorityKeyIdentifier=keyid,issuer
basicConstraints=CA:FALSE
keyUsage = digitalSignature, nonRepudiation, keyEncipherment, dataEncipherment
subjectAltName = @alt_names

[alt_names]
DNS.1 = server.berlin

서버 키 생성

# openssl req -new -sha256 -nodes -out server.csr -newkey rsa:2048 -keyout server.key -config <( cat server_rootCA.csr.cnf )

서버 인증서 생성

# openssl x509 -req -in server.csr -CA server_rootCA.pem -CAkey server_rootCA.key -CAcreateserial -out server.crt -days 3650 -sha256 -extfile v3.ext

Apache2 사이트 파일, HTTPS (포트 443) 섹션에 인증서 및 키 추가

SSLCertificateFile    /etc/apache2/ssl/server.crt
SSLCertificateKeyFile    /etc/apache2/ssl/server.key

server_rootCA.pem을 서버에서 시스템으로 복사하십시오.

# scp you@server.berlin:~/server_rootCA.pem .

.. Chromium 브라우저에 추가

Chromium -> Setting -> (Advanced) Manage Certificates -> Import -> 'server_rootCA.pem'

당신은 모두 끝났습니다!

PS 위의 지침에 따라 기능적인 CA 및 서버 인증서 쌍을 만드는 대신 HTTP 서버 구성에서 HSTS 헤더를 비활성화 할 수 있습니다. 이렇게하면 Chromium에서 HTTPS를 적용하지 못하게되며 사용자가 사용자 지정 CA (server_rootCA.pem) 인증서를 얻거나 설치하지 않고도“고급 → your.url로 진행 (안전하지 않음)”을 클릭 할 수 있습니다. 다시 말해서 – HSTS를 비활성화하면 HTTP 및 / 또는 안전하지 않은 HTTPS 연결을 통해 사이트를 공개적으로 볼 수 있습니다 (주의!).

Apache2의 경우 사이트 파일 HTTP (포트 80) 섹션에 다음을 추가하십시오.

Header unset Strict-Transport-Security
Header always set Strict-Transport-Security "max-age=0;includeSubDomains"

Debian / Apache2.4 + Debian / Chromium 59에서 테스트

https://ram.k0a1a.net/self-signed_https_cert_after_chrome_58


나중에 개별 인증서에 서명하는 루트 CA 기관의 경로를 사용하는 것이 크롬을 완전히 인증 할 수있는 유일한 방법입니다. 또한 사람들에게 단일 인증서를 설치하기 만하면된다는 이점이 있습니다. 감사합니다
geoff

4
누군가이 지역의 모든 사람들이 왜 -config <( cat server_rootCA.csr.cnf )대신 bashism을 사용하는 것처럼 보이는지 설명해 주 -config server_rootCA.csr.cnf시겠습니까?
Caesar

문제를 우회 할 수있는 아파치 헤더와 관련된 답변을 업데이트 할 수 있습니까? 가상 호스트 정의 내부에서 어디로 가야하는지 알 수 있습니까? 나는 여러 대안을 시도했지만 여전히 thorugh 사이트에 액세스 할 수 없습니다. 감사합니다
Nikos M.

12

이 작업을 수행하는 방법에 대한 예를 제공하는 몇 가지 훌륭한 답변이 있지만 시도에서 문제가 발생한 부분을 설명하는 것은 없습니다. OpenSSL은 때때로 직관적이지 않을 수 있으므로 살펴볼 가치가 있습니다.

먼저 OpenSSL은 기본적으로 구성에서 제공하는 고유 이름 값을 무시합니다. 그것들을 사용하려면 구성에 추가해야합니다 prompt = no . 또한 작성된 명령 은 인증서 자체가 아닌 인증서 요청 만 생성 하므로 -days아무 것도 수행하지 않습니다.

이 명령을 사용하여 인증서 요청을 생성하고 결과를 검사 한 경우 주제 대체 이름이 있습니다.

$ openssl req -new -key server.key -out server.csr -config config.cnf -sha256
$ openssl req -text -noout -in server.csr
Certificate Request:
    Data:
        Version: 1 (0x0)
        Subject: C = US, ST = Massachusetts, L = Boston, O = MyCompany
        Subject Public Key Info:
            Public Key Algorithm: rsaEncryption
                Public-Key: (2048 bit)
                Modulus:
                    ...
                Exponent: 65537 (0x10001)
        Attributes:
        Requested Extensions:
            X509v3 Subject Alternative Name:
                DNS:dev.mycompany.com
    Signature Algorithm: sha256WithRSAEncryption
         ...

그러나 heroku 링크의 명령을 사용하여 인증서를 생성하고 결과를 검사하면 주제 대체 이름이 누락됩니다.

$ openssl x509 -req -sha256 -days 365 -in server.csr -signkey server.key -out server.crt
$ openssl x509 -text -noout -in server.crt
Certificate:
    Data:
        Version: 1 (0x0)
        Serial Number:
            89:fd:75:26:43:08:04:61
    Signature Algorithm: sha256WithRSAEncryption
        Issuer: C = US, ST = Massachusetts, L = Boston, O = MyCompany
        Validity
            Not Before: Jan 21 04:27:21 2018 GMT
            Not After : Jan 21 04:27:21 2019 GMT
        Subject: C = US, ST = Massachusetts, L = Boston, O = MyCompany
        Subject Public Key Info:
            Public Key Algorithm: rsaEncryption
                Public-Key: (2048 bit)
                Modulus:
                    ...
                Exponent: 65537 (0x10001)
    Signature Algorithm: sha256WithRSAEncryption
         ...

기본적으로 OpenSSL은 확장을 요청에서 인증서로 복사하지 않기 때문입니다. 일반적으로 인증서는 고객의 요청에 따라 CA에서 작성 / 서명하며, 일부 확장은 요청에 정의 된 확장을 맹목적으로 신뢰하려는 경우 CA가 의도 한 것보다 더 많은 전원을 인증서에 부여 할 수 있습니다.

OpenSSL에 확장을 복사하도록 지시하는 방법이 있지만 IMHO는 인증서를 생성 할 때 구성 파일에 확장을 제공하는 것보다 더 효과적입니다.

기존 구성 파일을 사용하려고하면 최상위 레벨 섹션이 표시 [req]되어 해당 설정이 x509 명령이 아닌 req 명령에만 적용 되기 때문에 작동 하지 않습니다. 최상위 섹션 마커가 필요하지 않으므로 첫 번째 줄만 제거하면 요청이나 인증서 생성 모두에 잘 작동합니다.

$ openssl x509 -req -sha256 -days 365 -in server.csr -signkey server.key -out server.crt -extfile config.cnf

또는 명령에 대한 -x509인수를 사용하여 req먼저 요청을 작성한 다음 인증서를 작성하지 않고 단일 명령으로 자체 서명 된 인증서를 생성 할 수 있습니다 . 이 경우 [req]req 명령이 해당 섹션을 읽고 사용 하므로 섹션 라인 을 제거 할 필요가 없습니다 .

$ openssl req -x509 -sha256 -days 365 -key server.key -out server.crt -config config.cnf

요약하면, 위 명령에서 사용 된 수정 된 구성 파일은 다음과 같습니다.

default_bits        = 2048
distinguished_name  = dn
x509_extensions     = san
req_extensions      = san
extensions          = san
prompt              = no
[ dn ]
countryName         = US
stateOrProvinceName = Massachusetts
localityName        = Boston
organizationName    = MyCompany
[ san ]
subjectAltName      = DNS:dev.mycompany.com

2
이것이 SAN없이 인증서가 나온 이유를 이해하는 데 도움이 된 유일한 설명입니다 (제 경우에는 구성 파일에 x509_extensions를 포함해야했습니다)
Daniel Beardsmore

2

내 해결책은 기본을 그대로 유지하고 openssl.cnf마지막에 [ cert_www.example.com ]www.example.com이 인증서를 만들려는 웹 사이트 와 같은 새 섹션을 추가하는 subjectAltName것입니다. 다른 것). 물론 섹션 이름을 원하는대로 지정할 수 있습니다.

그런 다음 openssl req이전과 같이 명령을 실행하여 -extensions cert_www.example.com내용을 추가 -subj하고 모든 DN 정보를 직접 추가 합니다.

인증서 내용을 만든 후 및 사용하기 전에 인증서 내용을 확인하는 것을 잊지 마십시오. openssl x509 -text


1

구성이 구운 Bash 스크립트

bash를 사용하는 플랫폼에서 작동해야하는 쉘 스크립트입니다. HOSTNAME쉘에 대해 env를 설정하거나 선택한 호스트 이름을 제공한다고 가정 합니다 (예 :self_signed_cert.sh test

set -e

if [ -z "$1" ]; then
  hostname="$HOSTNAME"
else
  hostname="$1"
fi

local_openssl_config="
[ req ]
prompt = no
distinguished_name = req_distinguished_name
x509_extensions = san_self_signed
[ req_distinguished_name ]
CN=$hostname
[ san_self_signed ]
subjectAltName = DNS:$hostname, DNS:localhost
subjectKeyIdentifier = hash
authorityKeyIdentifier = keyid:always,issuer
basicConstraints = CA:true
keyUsage = nonRepudiation, digitalSignature, keyEncipherment, dataEncipherment, keyCertSign, cRLSign
extendedKeyUsage = serverAuth, clientAuth, timeStamping
"

openssl req \
  -newkey rsa:2048 -nodes \
  -keyout "$hostname.key.pem" \
  -x509 -sha256 -days 3650 \
  -config <(echo "$local_openssl_config") \
  -out "$hostname.cert.pem"
openssl x509 -noout -text -in "$hostname.cert.pem"

위의 내용은 최소한의 구성 파일 info openssl에 필요한 정보를 주입합니다.

DNS:localhost로컬 호스트를 통해보다 쉽게 ​​테스트 할 수 있도록 여분 의 SAN이 포함되어 있습니다. 원하지 않으면 스크립트에서 여분의 비트를 제거하십시오.

신용

bcardarella의 답변 은 훌륭합니다 ( 응답 이 충분하지 않아 의견을 말하거나 투표 할 수 없습니다). 그러나 대답은 플랫폼 고유의 기존 openssl 구성 파일 위치를 사용합니다.

나를 위해 작동

분명히, 주어진 플랫폼에 맞는 openssl 설정 파일을 찾아서 올바른 위치를 대체하면됩니다.

테스트

테스트하는 방법은 test.cert.pem에있는 Chrome 기관으로 가져 오세요 chrome://settings/certificates.

openssl s_server -key test.key.pem -cert test.cert.pem -accept 20443 -www &
openssl_pid=$!
google-chrome https://localhost:20443

그리고 테스트 후

kill $openssl_pid
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.