mirror of
				https://github.com/coredns/coredns.git
				synced 2025-10-31 10:13:14 -04:00 
			
		
		
		
	Deprecate multiple endpoints for out-of-cluster k8s api (#2454)
This fix deprecates endpoints for out-of-cluster k8s api, The Corefile still takes multiple endpoints though only the first one is used. A warning is shown if there are multiple endpoints. Signed-off-by: Yong Tang <yong.tang.github@outlook.com>
This commit is contained in:
		| @@ -32,7 +32,7 @@ all the zones the plugin should be authoritative for. | ||||
| ``` | ||||
| kubernetes [ZONES...] { | ||||
|     resyncperiod DURATION | ||||
|     endpoint URL [URL...] | ||||
|     endpoint URL | ||||
|     tls CERT KEY CACERT | ||||
|     kubeconfig KUBECONFIG CONTEXT | ||||
|     namespaces NAMESPACE... | ||||
| @@ -51,10 +51,6 @@ kubernetes [ZONES...] { | ||||
| * `resyncperiod` specifies the Kubernetes data API **DURATION** period. | ||||
| * `endpoint` specifies the **URL** for a remote k8s API endpoint. | ||||
|    If omitted, it will connect to k8s in-cluster using the cluster service account. | ||||
|    Multiple k8s API endpoints could be specified: | ||||
|    `endpoint http://k8s-endpoint1:8080 http://k8s-endpoint2:8080`. | ||||
|    CoreDNS will automatically perform a healthcheck and proxy to the healthy k8s API endpoint. | ||||
|    Note that only http is supported when more than one k8s API endpoints are specified at the moment. | ||||
| * `tls` **CERT** **KEY** **CACERT** are the TLS cert, key and the CA cert file names for remote k8s connection. | ||||
|    This option is ignored if connecting in-cluster (i.e. endpoint is not specified). | ||||
| * `kubeconfig` **KUBECONFIG** **CONTEXT** authenticates the connection to a remote k8s cluster using a kubeconfig file. It supports TLS, username and password, or token-based authentication. This option is ignored if connecting in-cluster (i.e., the endpoint is not specified). | ||||
|   | ||||
| @@ -6,15 +6,12 @@ import ( | ||||
| 	"fmt" | ||||
| 	"net" | ||||
| 	"strings" | ||||
| 	"sync/atomic" | ||||
| 	"time" | ||||
|  | ||||
| 	"github.com/coredns/coredns/plugin" | ||||
| 	"github.com/coredns/coredns/plugin/etcd/msg" | ||||
| 	"github.com/coredns/coredns/plugin/kubernetes/object" | ||||
| 	"github.com/coredns/coredns/plugin/pkg/dnsutil" | ||||
| 	"github.com/coredns/coredns/plugin/pkg/fall" | ||||
| 	"github.com/coredns/coredns/plugin/pkg/healthcheck" | ||||
| 	"github.com/coredns/coredns/plugin/pkg/upstream" | ||||
| 	"github.com/coredns/coredns/request" | ||||
|  | ||||
| @@ -174,50 +171,8 @@ func (k *Kubernetes) getClientConfig() (*rest.Config, error) { | ||||
| 	} | ||||
|  | ||||
| 	// Connect to API from out of cluster | ||||
| 	endpoint := k.APIServerList[0] | ||||
| 	if len(k.APIServerList) > 1 { | ||||
| 		// Use a random port for api proxy, will get the value later through listener.Addr() | ||||
| 		listener, err := net.Listen("tcp", "127.0.0.1:0") | ||||
| 		if err != nil { | ||||
| 			return nil, fmt.Errorf("failed to create kubernetes api proxy: %v", err) | ||||
| 		} | ||||
| 		k.APIProxy = &apiProxy{ | ||||
| 			listener: listener, | ||||
| 			handler: proxyHandler{ | ||||
| 				HealthCheck: healthcheck.HealthCheck{ | ||||
| 					FailTimeout: 3 * time.Second, | ||||
| 					MaxFails:    1, | ||||
| 					Path:        "/", | ||||
| 					Interval:    5 * time.Second, | ||||
| 				}, | ||||
| 			}, | ||||
| 		} | ||||
| 		k.APIProxy.handler.Hosts = make([]*healthcheck.UpstreamHost, len(k.APIServerList)) | ||||
| 		for i, entry := range k.APIServerList { | ||||
|  | ||||
| 			uh := &healthcheck.UpstreamHost{ | ||||
| 				Name: strings.TrimPrefix(entry, "http://"), | ||||
|  | ||||
| 				CheckDown: func(upstream *proxyHandler) healthcheck.UpstreamHostDownFunc { | ||||
| 					return func(uh *healthcheck.UpstreamHost) bool { | ||||
|  | ||||
| 						fails := atomic.LoadInt32(&uh.Fails) | ||||
| 						if fails >= upstream.MaxFails && upstream.MaxFails != 0 { | ||||
| 							return true | ||||
| 						} | ||||
| 						return false | ||||
| 					} | ||||
| 				}(&k.APIProxy.handler), | ||||
| 			} | ||||
|  | ||||
| 			k.APIProxy.handler.Hosts[i] = uh | ||||
| 		} | ||||
| 		k.APIProxy.Handler = &k.APIProxy.handler | ||||
|  | ||||
| 		// Find the random port used for api proxy | ||||
| 		endpoint = fmt.Sprintf("http://%s", listener.Addr()) | ||||
| 	} | ||||
| 	clusterinfo.Server = endpoint | ||||
| 	// Only the first one is used. We will deprecated multiple endpoints later. | ||||
| 	clusterinfo.Server = k.APIServerList[0] | ||||
|  | ||||
| 	if len(k.APICertAuth) > 0 { | ||||
| 		clusterinfo.CertificateAuthority = k.APICertAuth | ||||
|   | ||||
| @@ -195,15 +195,11 @@ func ParseStanza(c *caddy.Controller) (*Kubernetes, error) { | ||||
| 		case "endpoint": | ||||
| 			args := c.RemainingArgs() | ||||
| 			if len(args) > 0 { | ||||
| 				// Multiple endoints are deprecated but still could be specified, | ||||
| 				// only the first one be used, though | ||||
| 				k8s.APIServerList = args | ||||
| 				if len(args) > 1 { | ||||
| 					// If multiple endoints specified, then only http allowed | ||||
| 					for i := range args { | ||||
| 						parts := strings.SplitN(args[i], "://", 2) | ||||
| 						if len(parts) == 2 && parts[0] != "http" { | ||||
| 							return nil, fmt.Errorf("multiple endpoints can only accept http, found: %v", args[i]) | ||||
| 						} | ||||
| 					} | ||||
| 					log.Warningf("Multiple endpoints have been deprecated, only the first specified endpoint '%s' is used", args[0]) | ||||
| 				} | ||||
| 				continue | ||||
| 			} | ||||
|   | ||||
| @@ -394,19 +394,6 @@ kubernetes cluster.local`, | ||||
| 			podModeDisabled, | ||||
| 			fall.Zero, | ||||
| 		}, | ||||
| 		{ | ||||
| 			`kubernetes coredns.local { | ||||
|     endpoint http://localhost:9090 https://localhost:9091 | ||||
| }`, | ||||
| 			true, | ||||
| 			"multiple endpoints can only accept http", | ||||
| 			-1, | ||||
| 			-1, | ||||
| 			defaultResyncPeriod, | ||||
| 			"", | ||||
| 			podModeDisabled, | ||||
| 			fall.Zero, | ||||
| 		}, | ||||
| 	} | ||||
|  | ||||
| 	for i, test := range tests { | ||||
|   | ||||
		Reference in New Issue
	
	Block a user