-
Notifications
You must be signed in to change notification settings - Fork 39.6k
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
certs: only append locally discovered addresses when we get none from the cloudprovider #61869
Conversation
@mikedanese: Adding do-not-merge/release-note-label-needed because the release note process has not been followed. One of the following labels is required "release-note", "release-note-action-required", or "release-note-none". 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. |
pkg/kubelet/kubelet.go
Outdated
// If we successfully discovered addresses from the cloudprovider, use | ||
// those. Otherwise, use the configured addressed if provided. Otherwise, | ||
// make a best guess. | ||
if len(ips) != 0 || len(names) != 0 { |
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.
How could these ever not have len() == 0
? The var
block above creates zero length slices.
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.
Maybe
if len(cloudIPs) !=0 || len(cloudNames) != 0 {
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.
Ya that's right. I'll add a test :)
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, this function seems to be untested.
pkg/kubelet/kubelet.go
Outdated
if len(ips) != 0 || len(names) != 0 { | ||
ips = cloudIPs | ||
names = cloudNames | ||
} else if cfgAddress := net.ParseIP(kubeCfg.Address); cfgAddress != nil && !cfgAddress.IsUnspecified() { |
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 would have expected the explicitly configured address to override the cloud provider discovered ones. What's the motivation for having discovered addresses override the explicit ones?
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.
Ya, explicitly configured addresses should probably come first.
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.
/lgtm
… the cloudprovider The cloudprovider is right, and only cloudprovider addresses can be verified centrally, so don't add any extra.
/lgtm |
[APPROVALNOTIFIER] This PR is APPROVED This pull-request has been approved by: ericchiang, mikedanese, tallclair 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 |
/test all [submit-queue is verifying that this PR is safe to merge] |
Automatic merge from submit-queue (batch tested with PRs 54997, 61869, 61816, 61909, 60525). If you want to cherry-pick this change to another branch, please follow the instructions here. |
this doesn't work in combination with the way the kubelet reports addresses, which will fall back reporting a locally detected/overridden hostname address if the cloud provider doesn't specify one: kubernetes/pkg/kubelet/kubelet_node_status.go Lines 532 to 546 in ee2e11a
the kubelet needs to request a cert valid for the addresses it will report. it might be fine to omit the locally detected hostname in both places, but omitting only in one causes problems |
cc @awly |
opened #65585 to see what happens if we apply the same logic to node status |
|
||
// If the address was explicitly configured, use that. Otherwise, try to | ||
// discover addresses from the cloudprovider. Otherwise, make a best guess. | ||
if cfgAddress := net.ParseIP(kubeCfg.Address); cfgAddress != nil && !cfgAddress.IsUnspecified() { |
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.
this doesn't seem to make sense... isn't hostnameOverride an "explicit configuration" as well? why would --node-ip trump the cloud provider, and not --hostname-override? I could see making the cloud provider completely authoritative, but the ordering here doesn't make sense to me
edit: retracing this, this address isn't --node-ip
, it's --address
. that makes even less sense to have it override the cloud-provider-specified addresses.
kubelet node status jumps through a ton of hoops to derive an IP address to report:
// 1) Use nodeIP if set
// 2) If the user has specified an IP to HostnameOverride, use it
// 3) Lookup the IP from node name by DNS and use the first valid IPv4 address.
// If the node does not have a valid IPv4 address, use the first valid IPv6 address.
// 4) Try to get the IP from the network interface used as default gateway
if kl.nodeIP != nil {
ipAddr = kl.nodeIP
} else if addr := net.ParseIP(kl.hostname); addr != nil {
ipAddr = addr
} else {
var addrs []net.IP
addrs, _ = net.LookupIP(node.Name)
for _, addr := range addrs {
if err = kl.nodeIPValidator(addr); err == nil {
if addr.To4() != nil {
ipAddr = addr
break
}
if addr.To16() != nil && ipAddr == nil {
ipAddr = addr
}
}
}
if ipAddr == nil {
ipAddr, err = utilnet.ChooseHostInterface()
}
}
unfortunately, we have to match that here when requesting certs
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.
Updated #65585 to make this match as well
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.
long-term (hopefully in 1.12), we want to switch the serving cert request to react to changes in the node status, so that the node always has a valid cert (or a pending csr) for the addresses in the node status. that lets us contain the crazy address-computing code to one place, and also drive node addresses via an external cloud provider
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.
long-term (hopefully in 1.12)
turns out it was easier than expected. see #65594
Automatic merge from submit-queue. If you want to cherry-pick this change to another branch, please follow the instructions <a href="https://github.com/kubernetes/community/blob/master/contributors/devel/cherry-picks.md">here</a>. Revert "certs: only append locally discovered addresses when we got none from the cloudprovider" This reverts commit 7354bbe. #61869 caused a mismatch between the requested CSR and the addresses in node status. Instead of computing addresses in two places, the cert manager should derive its CSR request from the addresses in node status. This would enable the kubelet to react to address changes, as well as be driven by an external cloud provider. /cc @mikedanese ```release-note NONE ```
The cloudprovider is right, and only cloudprovider addresses can be verified centrally, so don't add any extra when we have them.