[Federation][init-10b] Update local kubeconfig with the new federation API server credentials.
This commit is contained in:
parent
8d8eca5f2a
commit
41b39f3019
@ -21,6 +21,8 @@ go_library(
|
||||
"//pkg/api/resource:go_default_library",
|
||||
"//pkg/apis/extensions:go_default_library",
|
||||
"//pkg/client/clientset_generated/internalclientset:go_default_library",
|
||||
"//pkg/client/unversioned/clientcmd:go_default_library",
|
||||
"//pkg/client/unversioned/clientcmd/api:go_default_library",
|
||||
"//pkg/kubectl/cmd/templates:go_default_library",
|
||||
"//pkg/kubectl/cmd/util:go_default_library",
|
||||
"//pkg/util/cert:go_default_library",
|
||||
@ -49,6 +51,7 @@ go_test(
|
||||
"//pkg/apis/extensions/v1beta1:go_default_library",
|
||||
"//pkg/client/restclient/fake:go_default_library",
|
||||
"//pkg/client/typed/dynamic:go_default_library",
|
||||
"//pkg/client/unversioned/clientcmd:go_default_library",
|
||||
"//pkg/kubectl/cmd/testing:go_default_library",
|
||||
"//pkg/kubectl/cmd/util:go_default_library",
|
||||
"//pkg/util/intstr:go_default_library",
|
||||
|
@ -42,6 +42,8 @@ import (
|
||||
"k8s.io/kubernetes/pkg/api/resource"
|
||||
"k8s.io/kubernetes/pkg/apis/extensions"
|
||||
client "k8s.io/kubernetes/pkg/client/clientset_generated/internalclientset"
|
||||
"k8s.io/kubernetes/pkg/client/unversioned/clientcmd"
|
||||
clientcmdapi "k8s.io/kubernetes/pkg/client/unversioned/clientcmd/api"
|
||||
"k8s.io/kubernetes/pkg/kubectl/cmd/templates"
|
||||
cmdutil "k8s.io/kubernetes/pkg/kubectl/cmd/util"
|
||||
certutil "k8s.io/kubernetes/pkg/util/cert"
|
||||
@ -56,6 +58,7 @@ import (
|
||||
const (
|
||||
APIServerCN = "federation-apiserver"
|
||||
ControllerManagerCN = "federation-controller-manager"
|
||||
AdminCN = "admin"
|
||||
HostClusterLocalDNSZoneName = "cluster.local."
|
||||
|
||||
lbAddrRetryInterval = 5 * time.Second
|
||||
@ -122,6 +125,7 @@ type entityKeyPairs struct {
|
||||
ca *triple.KeyPair
|
||||
server *triple.KeyPair
|
||||
controllerManager *triple.KeyPair
|
||||
admin *triple.KeyPair
|
||||
}
|
||||
|
||||
// initFederation initializes a federation control plane.
|
||||
@ -194,6 +198,11 @@ func initFederation(cmdOut io.Writer, config util.AdminConfig, cmd *cobra.Comman
|
||||
advertiseAddress = ips[0]
|
||||
}
|
||||
|
||||
endpoint := advertiseAddress
|
||||
if advertiseAddress == "" && len(hostnames) > 0 {
|
||||
endpoint = hostnames[0]
|
||||
}
|
||||
|
||||
// 6. Create federation API server
|
||||
_, err = createAPIServer(hostClientset, initFlags.FederationSystemNamespace, serverName, image, serverCredName, pvc.Name, advertiseAddress)
|
||||
if err != nil {
|
||||
@ -206,6 +215,13 @@ func initFederation(cmdOut io.Writer, config util.AdminConfig, cmd *cobra.Comman
|
||||
return err
|
||||
}
|
||||
|
||||
// 8. Write the federation API server endpoint info, credentials
|
||||
// and context to kubeconfig
|
||||
err = updateKubeconfig(config, initFlags.Name, endpoint, entKeyPairs)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
return printSuccess(cmdOut, ips, hostnames)
|
||||
}
|
||||
|
||||
@ -287,10 +303,15 @@ func genCerts(svcNamespace, name, svcName, localDNSZoneName string, ips, hostnam
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("failed to create federation controller manager client key and certificate: %v", err)
|
||||
}
|
||||
admin, err := triple.NewClientKeyPair(ca, AdminCN)
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("failed to create client key and certificate for an admin: %v", err)
|
||||
}
|
||||
return &entityKeyPairs{
|
||||
ca: ca,
|
||||
server: server,
|
||||
controllerManager: cm,
|
||||
admin: admin,
|
||||
}, nil
|
||||
}
|
||||
|
||||
@ -310,7 +331,6 @@ func createAPIServerCredentialsSecret(clientset *client.Clientset, namespace, cr
|
||||
|
||||
// Boilerplate to create the secret in the host cluster.
|
||||
return clientset.Core().Secrets(namespace).Create(secret)
|
||||
|
||||
}
|
||||
|
||||
func createControllerManagerKubeconfigSecret(clientset *client.Clientset, namespace, name, svcName, kubeconfigName string, entKeyPairs *entityKeyPairs) (*api.Secret, error) {
|
||||
@ -532,3 +552,44 @@ func printSuccess(cmdOut io.Writer, ips, hostnames []string) error {
|
||||
_, err := fmt.Fprintf(cmdOut, "Federation API server is running at: %s\n", strings.Join(svcEndpoints, ", "))
|
||||
return err
|
||||
}
|
||||
|
||||
func updateKubeconfig(config util.AdminConfig, name, endpoint string, entKeyPairs *entityKeyPairs) error {
|
||||
po := config.PathOptions()
|
||||
kubeconfig, err := po.GetStartingConfig()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
// Populate API server endpoint info.
|
||||
cluster := clientcmdapi.NewCluster()
|
||||
// Prefix "https" as the URL scheme to endpoint.
|
||||
if !strings.HasPrefix(endpoint, "https://") {
|
||||
endpoint = fmt.Sprintf("https://%s", endpoint)
|
||||
}
|
||||
cluster.Server = endpoint
|
||||
cluster.CertificateAuthorityData = certutil.EncodeCertPEM(entKeyPairs.ca.Cert)
|
||||
|
||||
// Populate credentials.
|
||||
authInfo := clientcmdapi.NewAuthInfo()
|
||||
authInfo.ClientCertificateData = certutil.EncodeCertPEM(entKeyPairs.admin.Cert)
|
||||
authInfo.ClientKeyData = certutil.EncodePrivateKeyPEM(entKeyPairs.admin.Key)
|
||||
authInfo.Username = AdminCN
|
||||
|
||||
// Populate context.
|
||||
context := clientcmdapi.NewContext()
|
||||
context.Cluster = name
|
||||
context.AuthInfo = name
|
||||
|
||||
// Update the config struct with API server endpoint info,
|
||||
// credentials and context.
|
||||
kubeconfig.Clusters[name] = cluster
|
||||
kubeconfig.AuthInfos[name] = authInfo
|
||||
kubeconfig.Contexts[name] = context
|
||||
|
||||
// Write the update kubeconfig.
|
||||
if err := clientcmd.ModifyConfig(po, *kubeconfig, true); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
@ -42,6 +42,7 @@ import (
|
||||
"k8s.io/kubernetes/pkg/apis/extensions/v1beta1"
|
||||
"k8s.io/kubernetes/pkg/client/restclient/fake"
|
||||
"k8s.io/kubernetes/pkg/client/typed/dynamic"
|
||||
"k8s.io/kubernetes/pkg/client/unversioned/clientcmd"
|
||||
cmdtesting "k8s.io/kubernetes/pkg/kubectl/cmd/testing"
|
||||
cmdutil "k8s.io/kubernetes/pkg/kubectl/cmd/util"
|
||||
"k8s.io/kubernetes/pkg/util/intstr"
|
||||
@ -125,6 +126,8 @@ func TestInitFederation(t *testing.T) {
|
||||
t.Errorf("[%d] expected error: %s, got: %s, output: %s", i, tc.expectedErr, cmdErrMsg, buf.String())
|
||||
}
|
||||
}
|
||||
|
||||
testKubeconfigUpdate(t, tc.federation, tc.lbIP, tc.kubeconfigGlobal, tc.kubeconfigExplicit)
|
||||
}
|
||||
}
|
||||
|
||||
@ -744,6 +747,60 @@ func fakeInitHostFactory(federationName, namespaceName, ip, dnsZoneName, image s
|
||||
return f, nil
|
||||
}
|
||||
|
||||
func testKubeconfigUpdate(t *testing.T, federationName, lbIP, kubeconfigGlobal, kubeconfigExplicit string) {
|
||||
filename := kubeconfigGlobal
|
||||
if kubeconfigExplicit != "" {
|
||||
filename = kubeconfigExplicit
|
||||
}
|
||||
config, err := clientcmd.LoadFromFile(filename)
|
||||
if err != nil {
|
||||
t.Errorf("Failed to open kubeconfig file: %v", err)
|
||||
return
|
||||
}
|
||||
|
||||
cluster, ok := config.Clusters[federationName]
|
||||
if !ok {
|
||||
t.Errorf("No cluster info for %q", federationName)
|
||||
return
|
||||
}
|
||||
endpoint := lbIP
|
||||
if !strings.HasSuffix(lbIP, "https://") {
|
||||
endpoint = fmt.Sprintf("https://%s", lbIP)
|
||||
}
|
||||
if cluster.Server != endpoint {
|
||||
t.Errorf("Want federation API server endpoint %q, got %q", endpoint, cluster.Server)
|
||||
}
|
||||
|
||||
authInfo, ok := config.AuthInfos[federationName]
|
||||
if !ok {
|
||||
t.Errorf("No credentials for %q", federationName)
|
||||
return
|
||||
}
|
||||
if len(authInfo.ClientCertificateData) == 0 {
|
||||
t.Errorf("Expected client certificate to be non-empty")
|
||||
return
|
||||
}
|
||||
if len(authInfo.ClientKeyData) == 0 {
|
||||
t.Errorf("Expected client key to be non-empty")
|
||||
return
|
||||
}
|
||||
if authInfo.Username != AdminCN {
|
||||
t.Errorf("Want username: %q, got: %q", AdminCN, authInfo.Username)
|
||||
}
|
||||
|
||||
context, ok := config.Contexts[federationName]
|
||||
if !ok {
|
||||
t.Errorf("No context for %q", federationName)
|
||||
return
|
||||
}
|
||||
if context.Cluster != federationName {
|
||||
t.Errorf("Want context cluster name: %q, got: %q", federationName, context.Cluster)
|
||||
}
|
||||
if context.AuthInfo != federationName {
|
||||
t.Errorf("Want context auth info: %q, got: %q", federationName, context.AuthInfo)
|
||||
}
|
||||
}
|
||||
|
||||
type clientServerTLSConfigs struct {
|
||||
server *tls.Config
|
||||
client *tls.Config
|
||||
|
Loading…
Reference in New Issue
Block a user