k8s.io/kubernetes@v1.31.0-alpha.0.0.20240520171757-56147500dadc/cmd/kubeadm/app/phases/uploadconfig/uploadconfig.go (about) 1 /* 2 Copyright 2017 The Kubernetes Authors. 3 4 Licensed under the Apache License, Version 2.0 (the "License"); 5 you may not use this file except in compliance with the License. 6 You may obtain a copy of the License at 7 8 http://www.apache.org/licenses/LICENSE-2.0 9 10 Unless required by applicable law or agreed to in writing, software 11 distributed under the License is distributed on an "AS IS" BASIS, 12 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 See the License for the specific language governing permissions and 14 limitations under the License. 15 */ 16 17 package uploadconfig 18 19 import ( 20 "fmt" 21 22 v1 "k8s.io/api/core/v1" 23 rbac "k8s.io/api/rbac/v1" 24 metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" 25 clientset "k8s.io/client-go/kubernetes" 26 27 kubeadmapi "k8s.io/kubernetes/cmd/kubeadm/app/apis/kubeadm" 28 kubeadmapiv1 "k8s.io/kubernetes/cmd/kubeadm/app/apis/kubeadm/v1beta3" 29 kubeadmconstants "k8s.io/kubernetes/cmd/kubeadm/app/constants" 30 "k8s.io/kubernetes/cmd/kubeadm/app/util/apiclient" 31 configutil "k8s.io/kubernetes/cmd/kubeadm/app/util/config" 32 ) 33 34 const ( 35 // NodesKubeadmConfigClusterRoleName sets the name for the ClusterRole that allows 36 // the bootstrap tokens to access the kubeadm-config ConfigMap during the node bootstrap/discovery 37 // or during upgrade nodes 38 NodesKubeadmConfigClusterRoleName = "kubeadm:nodes-kubeadm-config" 39 ) 40 41 // UploadConfiguration saves the InitConfiguration used for later reference (when upgrading for instance) 42 func UploadConfiguration(cfg *kubeadmapi.InitConfiguration, client clientset.Interface) error { 43 fmt.Printf("[upload-config] Storing the configuration used in ConfigMap %q in the %q Namespace\n", kubeadmconstants.KubeadmConfigConfigMap, metav1.NamespaceSystem) 44 45 // Prepare the ClusterConfiguration for upload 46 // The components store their config in their own ConfigMaps, then reset the .ComponentConfig struct; 47 // We don't want to mutate the cfg itself, so create a copy of it using .DeepCopy of it first 48 clusterConfigurationToUpload := cfg.ClusterConfiguration.DeepCopy() 49 clusterConfigurationToUpload.ComponentConfigs = kubeadmapi.ComponentConfigMap{} 50 51 // restore the resolved Kubernetes version as CI Kubernetes version if needed 52 if len(clusterConfigurationToUpload.CIKubernetesVersion) > 0 { 53 clusterConfigurationToUpload.KubernetesVersion = clusterConfigurationToUpload.CIKubernetesVersion 54 } 55 56 // Marshal the ClusterConfiguration into YAML 57 clusterConfigurationYaml, err := configutil.MarshalKubeadmConfigObject(clusterConfigurationToUpload, kubeadmapiv1.SchemeGroupVersion) 58 if err != nil { 59 return err 60 } 61 62 err = apiclient.CreateOrMutateConfigMap(client, &v1.ConfigMap{ 63 ObjectMeta: metav1.ObjectMeta{ 64 Name: kubeadmconstants.KubeadmConfigConfigMap, 65 Namespace: metav1.NamespaceSystem, 66 }, 67 Data: map[string]string{ 68 kubeadmconstants.ClusterConfigurationConfigMapKey: string(clusterConfigurationYaml), 69 }, 70 }, func(cm *v1.ConfigMap) error { 71 // Upgrade will call to UploadConfiguration with a modified KubernetesVersion reflecting the new 72 // Kubernetes version. In that case, the mutation path will take place. 73 cm.Data[kubeadmconstants.ClusterConfigurationConfigMapKey] = string(clusterConfigurationYaml) 74 return nil 75 }) 76 if err != nil { 77 return err 78 } 79 80 // Ensure that the NodesKubeadmConfigClusterRoleName exists 81 err = apiclient.CreateOrUpdateRole(client, &rbac.Role{ 82 ObjectMeta: metav1.ObjectMeta{ 83 Name: NodesKubeadmConfigClusterRoleName, 84 Namespace: metav1.NamespaceSystem, 85 }, 86 Rules: []rbac.PolicyRule{ 87 { 88 Verbs: []string{"get"}, 89 APIGroups: []string{""}, 90 Resources: []string{"configmaps"}, 91 ResourceNames: []string{kubeadmconstants.KubeadmConfigConfigMap}, 92 }, 93 }, 94 }) 95 if err != nil { 96 return err 97 } 98 99 // Binds the NodesKubeadmConfigClusterRoleName to all the bootstrap tokens 100 // that are members of the system:bootstrappers:kubeadm:default-node-token group 101 // and to all nodes 102 return apiclient.CreateOrUpdateRoleBinding(client, &rbac.RoleBinding{ 103 ObjectMeta: metav1.ObjectMeta{ 104 Name: NodesKubeadmConfigClusterRoleName, 105 Namespace: metav1.NamespaceSystem, 106 }, 107 RoleRef: rbac.RoleRef{ 108 APIGroup: rbac.GroupName, 109 Kind: "Role", 110 Name: NodesKubeadmConfigClusterRoleName, 111 }, 112 Subjects: []rbac.Subject{ 113 { 114 Kind: rbac.GroupKind, 115 Name: kubeadmconstants.NodeBootstrapTokenAuthGroup, 116 }, 117 { 118 Kind: rbac.GroupKind, 119 Name: kubeadmconstants.NodesGroup, 120 }, 121 }, 122 }) 123 }