Skip to content
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

Add --internal flag for export kubecfg that targets the internal dns name #9732

Merged
merged 1 commit into from
Aug 27, 2020

Conversation

rifelpet
Copy link
Member

@rifelpet rifelpet commented Aug 11, 2020

Kops creates an "api.internal.$clustername" dns A record that points to the master IP(s)

This adds a flag that will use that name and force the CA cert to be included.
This is a workaround for client certificate authentication not working on API ELBs with ACM certificates.
The ELB has a TLS listener rather than TCP, so the client certificate is not passed through to the apiserver.
Using --internal will bypass the API ELB so that the client certificate will be passed directly to the apiserver.

This also requires that the masters' security groups allow 443 access from the client which this does not handle automatically. I suppose if sslCertificateId is set, kops could automatically open 443 on the masters to the same sources that the ELB's 443 allows but I could see that being frowned upon for security reasons.

Fixes #800
(wow)

/hold for comment

@k8s-ci-robot k8s-ci-robot added do-not-merge/hold Indicates that a PR should not merge because someone has issued a /hold command. cncf-cla: yes Indicates the PR's author has signed the CNCF CLA. size/M Denotes a PR that changes 30-99 lines, ignoring generated files. labels Aug 11, 2020
@k8s-ci-robot
Copy link
Contributor

[APPROVALNOTIFIER] This PR is APPROVED

This pull-request has been approved by: rifelpet

The full list of commands accepted by this bot can be found here.

The pull request process is described here

Needs approval from an approver in each of these files:

Approvers can indicate their approval by writing /approve in a comment
Approvers can cancel approval by writing /approve cancel in a comment

@k8s-ci-robot k8s-ci-robot added area/documentation approved Indicates a PR has been approved by an approver from all required OWNERS files. labels Aug 11, 2020
@rifelpet rifelpet force-pushed the export-kubecfg-internal branch 3 times, most recently from 433c30e to 9632450 Compare August 12, 2020 00:58
@rifelpet
Copy link
Member Author

/retest

@@ -45,6 +45,9 @@ var (

# export using a user already existing in the kubeconfig file
kops export kubecfg kubernetes-cluster.example.com --user my-oidc-user

# export using the internal DNS name which bypasses the cloud load balancer
kops export kubecfg kubernetes-cluster.example.com --internal
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Maybe add a quick note here that you need an additional SG?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Or maybe should add by default 443 when sslCertificateId is enabled and export "internal"?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think that is a good idea!
Non-internal endpoints doesn't work anyway with this setup, right?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

the problem with modifying security groups is that kops export kubecfg is decoupled from where SG definitions are managed in kops update cluster. At update cluster time we don't know if the cluster operator will ever be running kops export kubecfg --internal. while we do generate the kubecfg in update cluster --yes, I suppose we could add the security group rule if the --internal flag is passed to update cluster but that could lead to confusion. Users running kops export kubecfg --internal would need to know to include --internal in their update cluster commands as well. I don't know if we have precedent for making a "pair" of commands require similar flags like that.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can we just add the port if sslCertificateId is enabled?
The export part can be explained in docs or printed at update cluster summary.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think always adding the rule if sslCertificateId is present might be reasonable. It assumes that anyone using an ACM cert will want the ability to use client cert auth for api access. I'm failing to think of scenarios in which that wouldn't be the case. I haven't looked into the code but I'm assuming we can use the same sources (CIDRs or SG IDs) we use on the API ELB for the instance 443 as well. I don't see a need to split that out into its own flag or diverge those settings.

One could go a step further and imply the --internal flag's behavior when exporting kubecfg if sslCertificateId and --admin are set. In fact 1.19 might be the best time to do that because the --admin flag is being added, so we could document this change in behavior along side the new flag.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

👍

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I could see a site with an alternate authentication provider not wanting the ability to use client cert auth from outside the cluster. But I see little reason to restrict anything that can hit the API ELB from hitting the instance's port 443.

I agree that sslCertificateId and --admin should imply the --internal flag's behavior.

Copy link
Member Author

@rifelpet rifelpet Aug 14, 2020

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

After more thought, creating the additional SG rules when kops update cluster --internal would be problematic for organizations in which multiple people run their kops commands manually. If someone were to forget to include --internal then kops would revoke the SG rules.

It would be much preferable to add the SG rules based on fields in the ClusterSpec. Either sslCertificateId being set or we add an additional field that allows users to toggle the behavior. Which we choose depends on if we think anyone using sslCertifiateId would not want the SG rules added.

Regardless, I think adding --internal while also implying --internal when sslCertificateId and --admin are used is a good idea.

cmd/kops/export_kubecfg.go Outdated Show resolved Hide resolved
docs/cluster_spec.md Outdated Show resolved Hide resolved
@rifelpet
Copy link
Member Author

The specific scenario in which we're relying on kubernetes api access with export kubecfg is our CI pipeline that runs rolling-update cluster. My concern with this approach is that as the masters are rolled, we're now more reliant on DNS TTLs to maintain API access which could be problematic. I haven't had the opportunity to test this yet (we just reenabled basic auth to unblock our upgrades), I'm hoping to do that before office hours.

@k8s-ci-robot k8s-ci-robot added the needs-rebase Indicates a PR cannot be merged because it has merge conflicts with HEAD. label Aug 15, 2020
@k8s-ci-robot k8s-ci-robot removed the needs-rebase Indicates a PR cannot be merged because it has merge conflicts with HEAD. label Aug 15, 2020
@k8s-ci-robot k8s-ci-robot added the needs-rebase Indicates a PR cannot be merged because it has merge conflicts with HEAD. label Aug 19, 2020
@k8s-ci-robot k8s-ci-robot removed the needs-rebase Indicates a PR cannot be merged because it has merge conflicts with HEAD. label Aug 27, 2020
…name

Kops creates an "api.internal.$clustername" dns A record that points to the master IP(s)

This adds a flag that will use that name and force the CA cert to be included.
This is a workaround for client certificate authentication not working on API ELBs with ACM certificates.
The ELB has a TLS listener rather than TCP, so the client certificate is not passed through to the apiserver.
Using --internal will bypass the API ELB so that the client certificate will be passed directly to the apiserver.
This also requires that the masters' security groups allow 443 access from the client which this does not handle automatically.
@rifelpet
Copy link
Member Author

I think this is ready for review. It isn't the ideal solution for the ACM certificate issue but the original ask was independent of that. We can go ahead and support this even with a better cert solution later on at which point we can update the cluster_spec.md text.

@hakman
Copy link
Member

hakman commented Aug 27, 2020

/lgtm

@k8s-ci-robot k8s-ci-robot added the lgtm "Looks good to me", indicates that a PR is ready to be merged. label Aug 27, 2020
@rifelpet
Copy link
Member Author

/hold cancel

@k8s-ci-robot k8s-ci-robot removed the do-not-merge/hold Indicates that a PR should not merge because someone has issued a /hold command. label Aug 27, 2020
@k8s-ci-robot k8s-ci-robot merged commit 3a75ecc into kubernetes:master Aug 27, 2020
@k8s-ci-robot k8s-ci-robot added this to the v1.19 milestone Aug 27, 2020
@rifelpet rifelpet deleted the export-kubecfg-internal branch May 5, 2021 13:43
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
approved Indicates a PR has been approved by an approver from all required OWNERS files. area/documentation cncf-cla: yes Indicates the PR's author has signed the CNCF CLA. lgtm "Looks good to me", indicates that a PR is ready to be merged. size/M Denotes a PR that changes 30-99 lines, ignoring generated files.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Support internal DNS names when exporting kubecfg
5 participants