-
Notifications
You must be signed in to change notification settings - Fork 18.8k
Description
I have a Kubernetes cluster running with a Nginx ingress controller. The ingress controller serves on port 80(for HTTP) and 443(for HTTPS).
An image registry is deployed on the Kubernetes cluster and it serves with HTTP using a virtual hostname(registry.local for example, the hostname is mapped to the domain name of ingress controller in the host where docker client runs).
When pushing images to the registry, according to the implement, docker tries to connect to https://registry.local, if it fails and then http://registry.local. But before retrying the HTTP server, there is a checking https://github.com/moby/moby/blob/master/distribution/push.go#L102:
if endpoint.URL.Scheme != "https" {
if _, confirmedTLS := confirmedTLSRegistries[endpoint.URL.Host]; confirmedTLS {
logrus.Debugf("Skipping non-TLS endpoint %s for host/port that appears to use TLS", endpoint.URL)
continue
}
}
Here is the problem comes from, as the ingress contoller serves on both HTTP and HTTPS, the host will be put into the map confirmedTLSRegistries
after trying HTTPS server https://github.com/moby/moby/blob/master/distribution/push.go#L124:
if fallbackErr.transportOK && endpoint.URL.Scheme == "https" {
confirmedTLSRegistries[endpoint.URL.Host] = struct{}{}
}
And this causes the HTTP one will not be tried.