github.com/IBM-Blockchain/fabric-operator@v1.0.4/pkg/manager/resources/deployment/deployment.go (about) 1 /* 2 * Copyright contributors to the Hyperledger Fabric Operator project 3 * 4 * SPDX-License-Identifier: Apache-2.0 5 * 6 * Licensed under the Apache License, Version 2.0 (the "License"); 7 * you may not use this file except in compliance with the License. 8 * You may obtain a copy of the License at: 9 * 10 * http://www.apache.org/licenses/LICENSE-2.0 11 * 12 * Unless required by applicable law or agreed to in writing, software 13 * distributed under the License is distributed on an "AS IS" BASIS, 14 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 15 * See the License for the specific language governing permissions and 16 * limitations under the License. 17 */ 18 19 package deployment 20 21 import ( 22 "fmt" 23 24 "github.com/IBM-Blockchain/fabric-operator/pkg/manager/resources/container" 25 "github.com/IBM-Blockchain/fabric-operator/pkg/util" 26 appsv1 "k8s.io/api/apps/v1" 27 v1 "k8s.io/api/apps/v1" 28 corev1 "k8s.io/api/core/v1" 29 ) 30 31 func New(deployment *v1.Deployment) *Deployment { 32 return &Deployment{ 33 Deployment: deployment, 34 } 35 } 36 37 type Deployment struct { 38 *v1.Deployment 39 } 40 41 func (d *Deployment) RemoveContainer(name string) { 42 for i, c := range d.Deployment.Spec.Template.Spec.Containers { 43 if c.Name == name { 44 if i == len(d.Deployment.Spec.Template.Spec.Containers)-1 { 45 d.Deployment.Spec.Template.Spec.Containers = d.Deployment.Spec.Template.Spec.Containers[:len(d.Deployment.Spec.Template.Spec.Containers)-1] 46 return 47 } 48 49 d.Deployment.Spec.Template.Spec.Containers = append( 50 d.Deployment.Spec.Template.Spec.Containers[:i], 51 d.Deployment.Spec.Template.Spec.Containers[i+1:]...) 52 return 53 } 54 } 55 } 56 57 func (d *Deployment) UpdateContainer(update container.Container) { 58 for i, c := range d.Deployment.Spec.Template.Spec.Containers { 59 if c.Name == update.Name { 60 d.Deployment.Spec.Template.Spec.Containers[i] = *update.Container 61 return 62 } 63 } 64 } 65 66 func (d *Deployment) UpdateInitContainer(update container.Container) { 67 for i, c := range d.Deployment.Spec.Template.Spec.InitContainers { 68 if c.Name == update.Name { 69 d.Deployment.Spec.Template.Spec.InitContainers[i] = *update.Container 70 return 71 } 72 } 73 } 74 75 func (d *Deployment) AddContainer(add container.Container) { 76 d.Deployment.Spec.Template.Spec.Containers = util.AppendContainerIfMissing(d.Deployment.Spec.Template.Spec.Containers, *add.Container) 77 } 78 79 func (d *Deployment) AddInitContainer(add container.Container) { 80 d.Deployment.Spec.Template.Spec.InitContainers = util.AppendContainerIfMissing(d.Deployment.Spec.Template.Spec.InitContainers, *add.Container) 81 } 82 83 func (d *Deployment) ContainerNames() []string { 84 names := []string{} 85 for _, c := range d.Deployment.Spec.Template.Spec.Containers { 86 names = append(names, c.Name) 87 } 88 for _, c := range d.Deployment.Spec.Template.Spec.InitContainers { 89 names = append(names, c.Name) 90 } 91 return names 92 } 93 94 func (d *Deployment) GetContainers() map[string]container.Container { 95 return container.LoadFromDeployment(d.Deployment) 96 } 97 98 func (d *Deployment) MustGetContainer(name string) container.Container { 99 cont, _ := d.GetContainer(name) 100 return cont 101 } 102 103 func (d *Deployment) GetContainer(name string) (cont container.Container, err error) { 104 for i, c := range d.Deployment.Spec.Template.Spec.Containers { 105 if c.Name == name { 106 cont = container.Container{Container: &d.Deployment.Spec.Template.Spec.Containers[i]} 107 return 108 } 109 } 110 for i, c := range d.Deployment.Spec.Template.Spec.InitContainers { 111 if c.Name == name { 112 cont = container.Container{Container: &d.Deployment.Spec.Template.Spec.InitContainers[i]} 113 return 114 } 115 } 116 return cont, fmt.Errorf("container '%s' not found", name) 117 } 118 119 func (d *Deployment) ContainerExists(name string) bool { 120 _, found := d.GetContainers()[name] 121 return found 122 } 123 124 func (d *Deployment) SetServiceAccountName(name string) { 125 d.Deployment.Spec.Template.Spec.ServiceAccountName = name 126 } 127 128 func (d *Deployment) SetImagePullSecrets(pullSecrets []string) { 129 if pullSecrets != nil && len(pullSecrets) > 0 { 130 d.Deployment.Spec.Template.Spec.ImagePullSecrets = []corev1.LocalObjectReference{} 131 132 for _, pullSecret := range pullSecrets { 133 imagePullSecret := corev1.LocalObjectReference{ 134 Name: pullSecret, 135 } 136 d.Deployment.Spec.Template.Spec.ImagePullSecrets = util.AppendImagePullSecretIfMissing(d.Deployment.Spec.Template.Spec.ImagePullSecrets, imagePullSecret) 137 } 138 } 139 } 140 141 func (d *Deployment) AppendPullSecret(imagePullSecret corev1.LocalObjectReference) { 142 d.Deployment.Spec.Template.Spec.ImagePullSecrets = util.AppendImagePullSecretIfMissing(d.Deployment.Spec.Template.Spec.ImagePullSecrets, imagePullSecret) 143 } 144 145 func (d *Deployment) AppendVolumeIfMissing(volume corev1.Volume) { 146 d.Deployment.Spec.Template.Spec.Volumes = util.AppendVolumeIfMissing(d.Deployment.Spec.Template.Spec.Volumes, volume) 147 } 148 149 func (d *Deployment) AppendPVCVolumeIfMissing(name, claimName string) { 150 volume := corev1.Volume{ 151 Name: name, 152 VolumeSource: corev1.VolumeSource{ 153 PersistentVolumeClaim: &corev1.PersistentVolumeClaimVolumeSource{ 154 ClaimName: claimName, 155 }, 156 }, 157 } 158 d.AppendVolumeIfMissing(volume) 159 } 160 161 func (d *Deployment) AppendConfigMapVolumeIfMissing(name, localObjReferenceName string) { 162 volume := corev1.Volume{ 163 Name: name, 164 VolumeSource: corev1.VolumeSource{ 165 ConfigMap: &corev1.ConfigMapVolumeSource{ 166 LocalObjectReference: corev1.LocalObjectReference{ 167 Name: localObjReferenceName, 168 }, 169 }, 170 }, 171 } 172 d.AppendVolumeIfMissing(volume) 173 } 174 175 func (d *Deployment) AppendSecretVolumeIfMissing(name, secretName string) { 176 volume := corev1.Volume{ 177 Name: name, 178 VolumeSource: corev1.VolumeSource{ 179 Secret: &corev1.SecretVolumeSource{ 180 SecretName: secretName, 181 }, 182 }, 183 } 184 d.AppendVolumeIfMissing(volume) 185 } 186 187 func (d *Deployment) AppendEmptyDirVolumeIfMissing(name string, storageMedium corev1.StorageMedium) { 188 volume := corev1.Volume{ 189 Name: name, 190 VolumeSource: corev1.VolumeSource{ 191 EmptyDir: &corev1.EmptyDirVolumeSource{ 192 Medium: storageMedium, 193 }, 194 }, 195 } 196 d.AppendVolumeIfMissing(volume) 197 } 198 199 func (d *Deployment) AppendHostPathVolumeIfMissing(name, hostPath string, hostPathType corev1.HostPathType) { 200 volume := corev1.Volume{ 201 Name: name, 202 VolumeSource: corev1.VolumeSource{ 203 HostPath: &corev1.HostPathVolumeSource{ 204 Path: hostPath, 205 Type: &hostPathType, 206 }, 207 }, 208 } 209 d.AppendVolumeIfMissing(volume) 210 } 211 212 func (d *Deployment) SetAffinity(affinity *corev1.Affinity) { 213 d.Deployment.Spec.Template.Spec.Affinity = affinity 214 } 215 216 func (d *Deployment) SetReplicas(replicas *int32) { 217 d.Deployment.Spec.Replicas = replicas 218 } 219 220 func (d *Deployment) SetStrategy(strategyType appsv1.DeploymentStrategyType) { 221 strategy := appsv1.DeploymentStrategy{ 222 Type: appsv1.RollingUpdateDeploymentStrategyType, 223 } 224 d.Deployment.Spec.Strategy = strategy 225 } 226 227 // UpdateSecurityContextForAllContainers updates the security context for all containers defined 228 // in the deployment 229 func (d *Deployment) UpdateSecurityContextForAllContainers(sc container.SecurityContext) { 230 for i := range d.Spec.Template.Spec.InitContainers { 231 container.UpdateSecurityContext(&d.Spec.Template.Spec.InitContainers[i], sc) 232 } 233 234 for i := range d.Spec.Template.Spec.Containers { 235 container.UpdateSecurityContext(&d.Spec.Template.Spec.Containers[i], sc) 236 } 237 }