-
Notifications
You must be signed in to change notification settings - Fork 30k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
doc: clarify tls.createServer's {cert, ca} #7230
Conversation
1. clarity cert to match bottom-half in src/node_crypto.cc setCert() calls SSL_CTX_use_certificate_chain() 2. clarity ca is to be used with requestCert Previously, nothing is mentioned about certificate chain, this may be confusing to beginners. They may pass intermediate certificates to ca option. If requestCert is false, this won't cause any problem. As bottom-half will try to find and insert intermediate certificates from ca store.
c133999
to
83c7a88
Compare
strings, or array of `Buffer`s containing the certificate key of the server | ||
in PEM format. (Required) | ||
strings, or array of `Buffer`s containing the server's certificate chain | ||
(server's certificate and intermediates) in PEM format. (Required) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The intermediates should be optional and they are preferably placed in ca
. IIRC, OpenSSL does accept both ways of adding them (concatenated vs. through ca
).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
a) Why is it preferable to place them in ca
? b) even if it is preferable, the ability to provide an entire cert chain here, and the order they should be in, must be documented and it isn't c) I'm about to rewrite much of this, the docs are in rough shape, and this is on my list of things to fix
clients that connect and attempt to verify that certificate. Defaults to | ||
`false`. | ||
clients that connect and attempt to verify that certificate against | ||
certificates provided in `ca` option. Defaults to `false`. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Not entirely correct. Node.js bundles Mozilla's root certificate bundle, which if I'm not mistaken are extended by the certificates provided by the ca
option.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The text is arguably correct, if you consider the ca option to have a default, the bundled certs. But its confusing.
@sliverwind the builtin certs aren't extended by the ca option, they are replaced (for this server)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Okay, then I totally misunderstood that option. If they are to be replaced, it certainly makes sense to provide a cert bundle instead.
@@ -965,7 +965,7 @@ const fs = require('fs'); | |||
|
|||
const options = { | |||
key: fs.readFileSync('server-key.pem'), | |||
cert: fs.readFileSync('server-cert.pem'), | |||
cert: fs.readFileSync('server-cert-chain.pem'), |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'd rather like to recommend using the ca
option here.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
why?
Sorry about the delay, we totally missed this one. I guess a bit more research is necessary on your side :) |
* `ca` {string|string[]|Buffer|Buffer[]} A string, `Buffer`, array of strings, | ||
or array of `Buffer`s of trusted certificates in PEM format. If this is | ||
omitted several well known "root" CAs (like VeriSign) will be used. These | ||
are used to authorize connections. | ||
are used to authorize connections. Useful for `requestCert` option. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
That isn't helpful, you need to describe what it does, and why what it does combines well with other options.
@wacky6 I'm -1 on this so far. Some of the text confuses instead of improving. Also, some of the text you improve is cut-n-paste multiple times in the doc, and you changed only one instance of the copies. Also, it leaves still many things about certs undocumented. You can keep at this, if you like, or wait for me to PR a more comprehensive set of changes. I do agree that the current docs are unusably incomplete. |
I think I should explain more on how I find this problem, sorry about my English writing. When I set up for TLS client authentication, I use: const tlsOpts = {
key: serverKey,
cert: serverCert,
ca: [ serverIntermediate, clientCA ],
requestCert: true
} In this setup, both server intermediate and client CA are sent to request certs. OpenSSL output looks like this:
Server Intermediate should not be used here to request client cert. I think we should clarify |
CA's usage is pretty much undocumented right now, it should be documented, I'm working on that. We can't change how these APIs work (not easily), so we do need to document that the intermediates can go in I agree with you, I'm curious as to why @silverwind thinks untrusted intermediate certs should be preferentially be put into the |
@sam-github no particular reason, I was under the wrong assumption that |
@silverwind we may have terminology mismaches.
ca is primarily for using privately issued certs, as opposed to certs with public trust roots. node contains the Mozilla collection of trust roots, so mostly its internal infrastructure/microservices that don't use certs purchased from CAs, and issue their own. In this case, client or server, you need to provide the private trust roots with the CA option.
Why recommend that? Doesn't it confuse things? If you look at @wacky6 's example above, wouldn't it boil down to saying something like:
That seems more complicated than "put trusted certs in Or do you look at it as "all certs that have the CA bit true should be in |
fixes nodejs#7230 Reviewed-By: James M Snell <jasnell@gmail.com> PR-URL: nodejs/node-v0.x-archive#25591
@sam-github @indutny are we certain that intermediate certs placed in a {
cert: [maincert, intermediate],
key: key
} And OpenSSL just gives me this:
On the other hand, this works as expected: {
cert: maincert,
key: key,
ca: [intermediate]
} I'm pretty sure we are either misdocumenting this and intermediates only work in |
They definitely work in the |
@indutny I'm pretty sure it's broken. Here's a test that uses a valid cert chain from a test CA I created: https://gist.github.com/silverwind/98d7b717617cbc52bce46498e351ec9f It failes with
|
Is that a valid cert chain? cert 0 and cert 1 have identical subject and issuer unless I am misreading your comment above, so cert 0 is not signed by cert 1. |
Yes (I was following https://jamielinux.com/docs/openssl-certificate-authority almost verbatim):
The issue should also be reproducible with any LetsEncrypt cert. |
That cert is self-signed, and has exactly the same subject/issuer pair as the intermediate cert, and the CA cert, I think the chain just confuses OpenSSL. Tests for cert chains with intermediate certs: #10747 |
I'm certain that the files in the example are not the cause of this |
@sam-github Here's an example using your certs. It fails to start with the dreaded
|
Okay I think this was actually just a misinterpretion of the docs on my side.
With the intermediate in a separate array entry, openssl gets rightly confused for the missing key. So I guess no action needed here. As for this PR: I'll close. Docs have been overhauled in the meanwhile and I guess it just doesn't apply anymore, sorry. |
fixes nodejs#7230 Reviewed-By: James M Snell <jasnell@gmail.com> PR-URL: nodejs/node-v0.x-archive#25565
Checklist
Affected core subsystem(s)
doc
Description of change
cert
to match bottom-halfin src/node_crypto.cc
setCert()
callsSSL_CTX_use_certificate_chain()
ca
is to be used withrequestCert