Mi sto perdendo qualcosa? È questo il modo corretto di costruire un certificato autofirmato?
È facile creare un certificato autofirmato. Basta usare il openssl req
comando. Può essere complicato crearne uno che può essere utilizzato dalla più grande selezione di client, come browser e strumenti da riga di comando.
È difficile perché i browser hanno i propri requisiti e sono più restrittivi di IETF . I requisiti utilizzati dai browser sono documentati nei forum CA / Browser (vedere i riferimenti di seguito). Le restrizioni sorgono in due aree chiave: (1) trust anchor e (2) nomi DNS.
I browser moderni (come il warez che stiamo usando nel 2014/2015) vogliono un certificato che ritorni su un ancoraggio sicuro e vogliono che i nomi DNS vengano presentati in modo particolare nel certificato. E i browser si stanno attivamente spostando rispetto ai certificati server autofirmati.
Alcuni browser non semplificano esattamente l'importazione di un certificato server autofirmato. In effetti, non è possibile con alcuni browser, come il browser Android. Quindi la soluzione completa è diventare la tua autorità.
In assenza di diventare la tua autorità, devi ottenere i nomi DNS giusti per dare al certificato le maggiori possibilità di successo. Ma ti incoraggio a diventare la tua autorità. È facile diventare la tua autorità e eluderà tutti i problemi di fiducia (di chi è meglio fidarsi di te stesso?).
Questo probabilmente non è il sito che stai cercando!
Il certificato di sicurezza del sito non è attendibile!
Questo perché i browser utilizzano un elenco predefinito di ancoraggi sicuri per convalidare i certificati del server. Un certificato autofirmato non si ricollega a un ancoraggio attendibile.
Il modo migliore per evitarlo è:
- Crea la tua autorità (ad esempio, diventa una CA. )
- Creare una richiesta di firma del certificato (CSR) per il server
- Firma il CSR del server con la tua chiave CA.
- Installa il certificato del server sul server
- Installa il certificato CA sul client
Passaggio 1: creare la propria autorità significa solo creare un certificato autofirmato con un CA: true
corretto utilizzo della chiave. Ciò significa che il Soggetto e l' Emittente sono la stessa entità, la CA è impostata su true nei Vincoli di base (deve anche essere contrassegnata come critica), l'utilizzo della chiave è keyCertSign
e crlSign
(se si utilizzano CRL) e l' identificatore chiave dell'oggetto (SKI) è lo stesso del dell'identificatore chiave autorità (AKI).
Per diventare la propria autorità di certificazione, vedere * Come si firma una richiesta di firma del certificato con la propria autorità di certificazione?su Stack Overflow. Quindi, importa la tua CA nel Trust Store utilizzato dal browser.
I passaggi 2 - 4 sono all'incirca quelli che fai ora per un server pubblico quando aggiungi i servizi di una CA come Startcom o CAcert . I passaggi 1 e 5 ti consentono di evitare l'autorità di terze parti e di agire come la tua autorità (di chi è meglio fidarsi di te stesso?).
Il prossimo modo migliore per evitare l'avviso del browser è fidarsi del certificato del server. Ma alcuni browser, come il browser predefinito di Android, non ti consentono di farlo. Quindi non funzionerà mai sulla piattaforma.
Il problema dei browser (e altri agenti utente simili) no fidano dei certificati autofirmati sarà un grosso problema nell'Internet of Things (IoT). Ad esempio, cosa accadrà quando ci si collega al termostato o al frigorifero per programmarlo? La risposta è: nulla di buono per quanto riguarda l'esperienza dell'utente.
Il gruppo di lavoro WebAppSec del W3C sta iniziando a esaminare il problema. Vedere, ad esempio, Proposta: contrassegnare HTTP come non sicuro .
Come creare un certificato autofirmato con OpenSSL
I comandi seguenti e il file di configurazione creano un certificato autofirmato (mostra anche come creare una richiesta di firma). Differiscono dalle altre risposte per un aspetto: i nomi DNS utilizzati per il certificato autofirmato si trovano nel soggetto Nome alternativo (SAN) e non nel nome comune (CN) .
I nomi DNS vengono inseriti nella SAN attraverso il file di configurazione con la linea subjectAltName = @alternate_names
(non c'è modo di farlo attraverso la riga di comando). Quindi c'è una alternate_names
sezione nel file di configurazione (dovresti regolarla secondo i tuoi gusti):
[ 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
È importante inserire il nome DNS nella SAN e non nella CN, poiché sia IETF che i forum CA / Browser specificano la pratica. Inoltre, specificano che i nomi DNS nella CN sono obsoleti (ma non vietati). Se si inserisce un nome DNS nella CN, deve essere incluso nella SAN in base ai criteri CA / B. Quindi non puoi evitare di usare il Nome alternativo soggetto.
Se non si inseriscono nomi DNS nella SAN, il certificato non verrà convalidato in un browser e altri agenti utente che seguono le linee guida CA / Forum Forum.
Correlati: i browser seguono le politiche CA / Browser Forum; e non le politiche IETF. Questo è uno dei motivi per cui un certificato creato con OpenSSL (che generalmente segue la IETF) a volte non viene convalidato da un browser (i browser seguono la CA / B). Sono standard diversi, hanno politiche di emissione e requisiti di convalida diversi.
Crea un certificato autofirmato (nota l'aggiunta -x509
dell'opzione):
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
Crea una richiesta di firma (nota la mancanza di -x509
opzione):
openssl req -config example-com.conf -new -sha256 -newkey rsa:2048 -nodes \
-keyout example-com.key.pem -days 365 -out example-com.req.pem
Stampa un certificato autofirmato :
openssl x509 -in example-com.cert.pem -text -noout
Stampa una richiesta di firma :
openssl req -in example-com.req.pem -text -noout
File di configurazione (passato tramite -config
opzione)
[ 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
Potrebbe essere necessario eseguire le seguenti operazioni per Chrome. Altrimenti Chrome potrebbe lamentare un nome comune non valido ( ERR_CERT_COMMON_NAME_INVALID
) . Non sono sicuro di quale sia la relazione tra un indirizzo IP nella SAN e una CN in questo caso.
# IPv4 localhost
# IP.1 = 127.0.0.1
# IPv6 localhost
# IP.2 = ::1
Esistono altre regole relative alla gestione dei nomi DNS nei certificati X.509 / PKIX. Fare riferimento a questi documenti per le regole:
Sono elencati RFC 6797 e RFC 7469, poiché sono più restrittivi rispetto agli altri documenti RFC e CA / B. Le RFC 6797 e 7469 non consentono neanche un indirizzo IP.