-
Notifications
You must be signed in to change notification settings - Fork 1.6k
Add section on supporting intermediate certificates #1615
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
Conversation
|
[APPROVALNOTIFIER] This PR is NOT APPROVED This pull-request has been approved by: jackkleeman The full list of commands accepted by this bot can be found here.
Needs approval from an approver in each of these files:
Approvers can indicate their approval by writing |
|
/assign @mikedanese |
| #### Supporting intermediate certificates. | ||
| It's important that the Certificates API fully supports using an intermediate certificate as the signer, including the case where the signer is itself signed by an intermediate. As a result, the user must be able to specify that the signing certificates are provided to the client, in which case their PEM values would be appended to the Certificate in the CertificateSigningRequestStatus. Conforming clients will parse the full chain of certificates provided by the apiserver and present them all for new TLS handshakes. | ||
|
|
||
| Firstly, we will add a new bool flag to the controller, `cluster-signing-include-signers`, which requires that the signing certificate is always appended in this way. Currently the controller only allows a single signing cert in `cluster-signing-cert-file`, so this approach would only work in the case where the signing certificate is a child of the root CA, in which case it is the only certificate that needs to be provided to the client. To support further nested signing certificates, we additionally need to relax the contraint of the cert file parameter to accept multiple signers in a chain. The additional certificates would only be used if the include signers option is set; they are not needed in signing. |
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.
nit: if you wrap at 80/120 LoC, it makes it a little easier to review/discuss :)
The additional certificates would only be used if the include signers option is set; they are not needed in signing.
It seems non-obvious to have the --cluster-signing-cert-file parameter specifically say that "some of these things actually won't be used for signing".
I may have missed something in previous discussion, but what's the rationale behind a bool vs an explicit --cluster-signing-cert-chain flag which points to a file containing the chain expected to be appended to the certificates the signer signs? I know this was talked about before and I thought the consensus was on an explicit file/flag.
To try and get an idea of what either configuration would look like either way...
With the bool:
- single self signed root: configure as we do today (no
--cluster-signing-include-signersflag - root -> intermediate:
--cluster-signing-cert-file=<path-to-intermediate>--cluster-signing-include-signers=true - root -> intermediate -> intermediate:
--cluster-signing-cert-file=<path-to-file-with-both-intermediates>--cluster-signing-include-signers=true
& with the additional file flag:
- single self signed root: configure as we do today (no
--cluster-signing-chain-fileflag - root -> intermediate:
--cluster-signing-cert-file=<path-to-intermediate>--cluster-signing-chain-file=<path-to-intermediate> - root -> intermediate1 -> intermediate2:
--cluster-signing-cert-file=<path-to-intermediate2-file>--cluster-signing-chain-file=<path-to-file-with-both-intermediates>
I think the bool option isn't actually that unclear for anyone with some PKI background (who is familiar with concatenating PEM files together), although the fact that --cluster-signing-key-file and --cluster-signing-cert-file now are a bit ambiguous could definitely cause confusion (one of these can contain multiple certificates, the other contains a private key that must be valid with the first intermediate only).
The additional file option seems a bit more verbose, but at least it is explicit (and validation in kube-controller-manager could check to ensure that only a single PEM is included in the --cluster-signing-cert-file too)
More of a brain dump than a concrete answer/review :)
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 like the file option too, but the spanner in the works for me was:
- In probably(?) the most common case where you're not signing with a root, you have root -> intermediate. In that case, you provide the same file to two different parameters, which just feels weird to me as an end user
- As an addendum to that, managing rotation of these files becomes more complicated; we now have two files that can contain overlapping content or may be the same file, where we're generally interested in the deduplicated sum of both files. We can't set up individual file rotation controllers on them, we'd need to do something bespoke to watch them together, although there will technically always be a race condition that needs to be handled
It just feels simpler to me to have all the certs in one place, and let people decide whether to include them in the cert response. To be honest, I'd advocate to include signing certs by default, maybe filtering out any root certs, but its not as explicit.
|
Intermediates can include a set larger than the simply the certificate that was used for signing. If we're going to add a flag, it makes sense for it cover the full use-case. In addition, with four distinct signers from the migration of a single-signer, flags should take into account the reality of managing distinct signers. There is clear value to having these separate signers with their own signing cert/keys (trust, revocation, and duration of the signer validity) and each would logically have their own intermediates. We get a choice between a proliferation of flags or names configurable in a repeated flag. Either can be constrained via validation to avoid runaway, "sign all the things" usage. I'd like to see this enhancement updated to reflect the larger context of the problem-space it exists in. |
Does this part of my patch cover this particular concern? I agree we need to allow a set of intermediates that can also be provided to the client, and I wonder if we can do this by simply allowing a full chain to be provided as the cert file. |
Not really. The first concern is that intermediates encompass more than just the signer, which implies another flag. The second concern is that we would need such a parallel flag for each signer we support configuring. I don't know enough about cert signing standards to know if it is normal to auto-choose which certificate in a bundle to sign with. It sounds unusual to me, but I'm not sure if it is normal and simply uncommon enough that I haven't seen it. |
|
Please include changes you intend to make to the CertificateSigningRequest API Definition (even if they are only doc changes). |
|
@mikedanese I think its already covered by the comment in this kep: but this is not currently the comment in k8s/k8s. The main concern is how we set up the configuration, I believe the kep already covers conceptually how intermediates are handled in the api. |
sftim
left a comment
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 couple of questions for clarification.
| It's important that the Certificates API fully supports using an intermediate certificate as the signer, | ||
| including the case where the signer is itself signed by an intermediate. As a result, the user must be able | ||
| to specify that the signing certificates are provided to the client, in which case their PEM values would | ||
| be appended to the Certificate in the CertificateSigningRequestStatus. Conforming clients will parse the |
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 recommend unambiguously specify the order in which intermediate certs are added into CertificateSigningRequest's status field or stating that the order is arbitrary / random.
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.
Hmm, we could say it's the order given in the file in the controller, but I'm tempted to not make any guarantees here. I can update to say that it's arbitrary
| be appended to the Certificate in the CertificateSigningRequestStatus. Conforming clients will parse the | ||
| full chain of certificates provided by the apiserver and present them all for new TLS handshakes. | ||
|
|
||
| Firstly, we will add a new bool flag to the controller, `cluster-signing-include-signers`, which requires |
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.
Is this a boolean field in the CSR spec or a boolean command line argument to the kube-controller-manager?
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 latter, I can clarify
|
Another compelling reason to add a new flag for the intermediate bundle is that we can't easily introduce the full set of validation we could do on an existing flag. I do like the idea of validating that intermediate bundle is a single, well formed chain up to a root. This validation would break kcms that are configured with an intermediate cert today if we reuse
I don't see support for auto-selection in openssl or cfssl. We would be relaxing the validation of the signing configuration in order to reuse an option for the bundling phase. I'm leaning towards a separate options. |
Should signers include or omit root certs in the bundle? The doc indicates that it won't. Is that what we want? |
Personally I see no reason to send the root given that there's no reason for clients to present it, but I guess it wouldn't hurt, if others disagree |
|
I would avoid sending the root in the CSR... that seems likely to lead to inappropriate use as a trust distribution mechanism |
|
Not including roots makes sense to me. |
NSS handles a similar situation (designation of a valid signer in a full chain) with a trust flag setting, where one of the flags means "this CA can be used to sign". So on the signer side of things, having a full chain but providing an option to select the CA is not unheard of. I'd say it's better to not send the root in a chain back to the requester, it's implied that they have the root by other means (i.e. browser bundle), but may not have the intermediate chain that was the CA's choosing. Although, if you have a chain of root->sub1->sub2->sub3 and sub3 is used to sign, you might not want to even send back sub1 and sub2 if they can be used alone as valid trust anchors (golang clients allow this). So depending on the clients, sending intermediates may also be used as trust distribution.. |
|
Issues go stale after 90d of inactivity. If this issue is safe to close now please do so with Send feedback to sig-testing, kubernetes/test-infra and/or fejta. |
|
@jackkleeman: PR needs rebase. Instructions for interacting with me using PR comments are available here. If you have questions or suggestions related to my behavior, please file an issue against the kubernetes/test-infra repository. |
|
Stale issues rot after 30d of inactivity. If this issue is safe to close now please do so with Send feedback to sig-testing, kubernetes/test-infra and/or fejta. |
|
@jackkleeman - do you have time to rebase this and help it move forward? It sounds like a good idea. |
|
Rotten issues close after 30d of inactivity. Send feedback to sig-testing, kubernetes/test-infra and/or fejta. |
|
@fejta-bot: Closed this PR. In response to this:
Instructions for interacting with me using PR comments are available here. If you have questions or suggestions related to my behavior, please file an issue against the kubernetes/test-infra repository. |
this-week: 2024-04-26
I've written my proposal for how we could support intermediate certificates, which is already partially implemented in kubernetes/kubernetes#88741.
There's already been a lot of different ideas about the right design here, so this is just intended to spur discussion, I'm happy to write up whatever conclusion we come to.
Here's the bit thats causing confusion:
We have a signing certificate, currently inputed as a file, with another file for a key. We want users to be able to indicate, optionally, that the signing certificate should be presented back to the client. However, for this to be useful in cases with a long chain up to the root, we need to also allow the user to provide additional intermediate certificates (closer to the root than the signer), that can be used to build a chain to the root. There are a few options, and we'd love input from people who have worked with a similar system.