k8s.io/client-go@v0.22.2/examples/create-update-delete-deployment/main.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 // Note: the example only works with the code within the same release/branch. 18 package main 19 20 import ( 21 "bufio" 22 "context" 23 "flag" 24 "fmt" 25 "os" 26 "path/filepath" 27 28 appsv1 "k8s.io/api/apps/v1" 29 apiv1 "k8s.io/api/core/v1" 30 metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" 31 "k8s.io/client-go/kubernetes" 32 "k8s.io/client-go/tools/clientcmd" 33 "k8s.io/client-go/util/homedir" 34 "k8s.io/client-go/util/retry" 35 // 36 // Uncomment to load all auth plugins 37 // _ "k8s.io/client-go/plugin/pkg/client/auth" 38 // 39 // Or uncomment to load specific auth plugins 40 // _ "k8s.io/client-go/plugin/pkg/client/auth/azure" 41 // _ "k8s.io/client-go/plugin/pkg/client/auth/gcp" 42 // _ "k8s.io/client-go/plugin/pkg/client/auth/oidc" 43 // _ "k8s.io/client-go/plugin/pkg/client/auth/openstack" 44 ) 45 46 func main() { 47 var kubeconfig *string 48 if home := homedir.HomeDir(); home != "" { 49 kubeconfig = flag.String("kubeconfig", filepath.Join(home, ".kube", "config"), "(optional) absolute path to the kubeconfig file") 50 } else { 51 kubeconfig = flag.String("kubeconfig", "", "absolute path to the kubeconfig file") 52 } 53 flag.Parse() 54 55 config, err := clientcmd.BuildConfigFromFlags("", *kubeconfig) 56 if err != nil { 57 panic(err) 58 } 59 clientset, err := kubernetes.NewForConfig(config) 60 if err != nil { 61 panic(err) 62 } 63 64 deploymentsClient := clientset.AppsV1().Deployments(apiv1.NamespaceDefault) 65 66 deployment := &appsv1.Deployment{ 67 ObjectMeta: metav1.ObjectMeta{ 68 Name: "demo-deployment", 69 }, 70 Spec: appsv1.DeploymentSpec{ 71 Replicas: int32Ptr(2), 72 Selector: &metav1.LabelSelector{ 73 MatchLabels: map[string]string{ 74 "app": "demo", 75 }, 76 }, 77 Template: apiv1.PodTemplateSpec{ 78 ObjectMeta: metav1.ObjectMeta{ 79 Labels: map[string]string{ 80 "app": "demo", 81 }, 82 }, 83 Spec: apiv1.PodSpec{ 84 Containers: []apiv1.Container{ 85 { 86 Name: "web", 87 Image: "nginx:1.12", 88 Ports: []apiv1.ContainerPort{ 89 { 90 Name: "http", 91 Protocol: apiv1.ProtocolTCP, 92 ContainerPort: 80, 93 }, 94 }, 95 }, 96 }, 97 }, 98 }, 99 }, 100 } 101 102 // Create Deployment 103 fmt.Println("Creating deployment...") 104 result, err := deploymentsClient.Create(context.TODO(), deployment, metav1.CreateOptions{}) 105 if err != nil { 106 panic(err) 107 } 108 fmt.Printf("Created deployment %q.\n", result.GetObjectMeta().GetName()) 109 110 // Update Deployment 111 prompt() 112 fmt.Println("Updating deployment...") 113 // You have two options to Update() this Deployment: 114 // 115 // 1. Modify the "deployment" variable and call: Update(deployment). 116 // This works like the "kubectl replace" command and it overwrites/loses changes 117 // made by other clients between you Create() and Update() the object. 118 // 2. Modify the "result" returned by Get() and retry Update(result) until 119 // you no longer get a conflict error. This way, you can preserve changes made 120 // by other clients between Create() and Update(). This is implemented below 121 // using the retry utility package included with client-go. (RECOMMENDED) 122 // 123 // More Info: 124 // https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#concurrency-control-and-consistency 125 126 retryErr := retry.RetryOnConflict(retry.DefaultRetry, func() error { 127 // Retrieve the latest version of Deployment before attempting update 128 // RetryOnConflict uses exponential backoff to avoid exhausting the apiserver 129 result, getErr := deploymentsClient.Get(context.TODO(), "demo-deployment", metav1.GetOptions{}) 130 if getErr != nil { 131 panic(fmt.Errorf("Failed to get latest version of Deployment: %v", getErr)) 132 } 133 134 result.Spec.Replicas = int32Ptr(1) // reduce replica count 135 result.Spec.Template.Spec.Containers[0].Image = "nginx:1.13" // change nginx version 136 _, updateErr := deploymentsClient.Update(context.TODO(), result, metav1.UpdateOptions{}) 137 return updateErr 138 }) 139 if retryErr != nil { 140 panic(fmt.Errorf("Update failed: %v", retryErr)) 141 } 142 fmt.Println("Updated deployment...") 143 144 // List Deployments 145 prompt() 146 fmt.Printf("Listing deployments in namespace %q:\n", apiv1.NamespaceDefault) 147 list, err := deploymentsClient.List(context.TODO(), metav1.ListOptions{}) 148 if err != nil { 149 panic(err) 150 } 151 for _, d := range list.Items { 152 fmt.Printf(" * %s (%d replicas)\n", d.Name, *d.Spec.Replicas) 153 } 154 155 // Delete Deployment 156 prompt() 157 fmt.Println("Deleting deployment...") 158 deletePolicy := metav1.DeletePropagationForeground 159 if err := deploymentsClient.Delete(context.TODO(), "demo-deployment", metav1.DeleteOptions{ 160 PropagationPolicy: &deletePolicy, 161 }); err != nil { 162 panic(err) 163 } 164 fmt.Println("Deleted deployment.") 165 } 166 167 func prompt() { 168 fmt.Printf("-> Press Return key to continue.") 169 scanner := bufio.NewScanner(os.Stdin) 170 for scanner.Scan() { 171 break 172 } 173 if err := scanner.Err(); err != nil { 174 panic(err) 175 } 176 fmt.Println() 177 } 178 179 func int32Ptr(i int32) *int32 { return &i }