Skip to content

Commit f1b00cb

Browse files
committed
review comments
1 parent 8b28d0d commit f1b00cb

File tree

2 files changed

+98
-109
lines changed

2 files changed

+98
-109
lines changed

internal/controller/utils.go

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -67,3 +67,16 @@ func getPodTemplateSpec(raw []byte, path string) (*v1.PodTemplateSpec, error) {
6767

6868
return template, nil
6969
}
70+
71+
// return the subobject found at the given path, or nil if the path is invalid
72+
func getSubObject(obj map[string]interface{}, path string) map[string]interface{} {
73+
parts := strings.Split(path, ".")
74+
var ok bool
75+
for i := 1; i < len(parts); i++ {
76+
obj, ok = obj[parts[i]].(map[string]interface{})
77+
if !ok {
78+
return nil
79+
}
80+
}
81+
return obj
82+
}

internal/controller/workload_controller.go

Lines changed: 85 additions & 109 deletions
Original file line numberDiff line numberDiff line change
@@ -17,10 +17,8 @@ limitations under the License.
1717
package controller
1818

1919
import (
20-
"encoding/json"
2120
"fmt"
2221
"maps"
23-
"strings"
2422

2523
"k8s.io/apimachinery/pkg/api/meta"
2624
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
@@ -108,82 +106,72 @@ func (aw *AppWrapper) RunWithPodSetsInfo(podSetsInfo []podset.PodSetInfo) error
108106

109107
for _, podSet := range component.PodSets {
110108
podSetsInfoIndex += 1
111-
if podSetsInfoIndex <= len(podSetsInfo) {
112-
toInject := podSetsInfo[podSetsInfoIndex-1]
113-
parts := strings.Split(podSet.Path, ".")
114-
p := obj.UnstructuredContent()
115-
var ok bool
116-
for i := 1; i < len(parts); i++ {
117-
p, ok = p[parts[i]].(map[string]interface{})
118-
if !ok {
119-
return fmt.Errorf("path element %v not found (segment %v of %v)", parts[i], i, len(parts))
120-
}
121-
}
122-
objChanged = true // Even if currentInfo is empty, we will still add appWrapperLabel to p.metadata.labels
109+
if podSetsInfoIndex > len(podSetsInfo) {
110+
continue
111+
}
123112

124-
if _, ok := p["metadata"]; !ok {
125-
p["metadata"] = make(map[string]interface{})
126-
}
127-
metadata := p["metadata"].(map[string]interface{})
113+
objChanged = true // We set p.metadata.labels[appWrapperLabel] = aw.Name irrespective of the content of toInject
114+
toInject := podSetsInfo[podSetsInfoIndex-1]
115+
p := getSubObject(obj.UnstructuredContent(), podSet.Path)
116+
if p == nil {
117+
return fmt.Errorf("path %v not found in component %v", podSet.Path, component)
118+
}
128119

129-
// Annotations
130-
if len(toInject.Annotations) > 0 {
131-
if _, ok := metadata["annotations"]; !ok {
132-
metadata["annotations"] = make(map[string]string)
133-
}
134-
annotations := metadata["annotations"].(map[string]string)
135-
if err := utilmaps.HaveConflict(annotations, toInject.Annotations); err != nil {
120+
if _, ok := p["metadata"]; !ok {
121+
p["metadata"] = make(map[string]interface{})
122+
}
123+
metadata := p["metadata"].(map[string]interface{})
124+
125+
// Annotations
126+
if len(toInject.Annotations) > 0 {
127+
if annotations, ok := metadata["annotations"]; ok {
128+
metadata["annotations"] = maps.Clone(toInject.Annotations)
129+
} else {
130+
if err := utilmaps.HaveConflict(annotations.(map[string]string), toInject.Annotations); err != nil {
136131
return podset.BadPodSetsUpdateError("annotations", err)
137132
}
138-
metadata["annotations"] = utilmaps.MergeKeepFirst(annotations, toInject.Annotations)
133+
metadata["annotations"] = utilmaps.MergeKeepFirst(metadata["annotations"].(map[string]string), toInject.Annotations)
139134
}
135+
}
140136

141-
// Labels
142-
if _, ok := metadata["labels"]; !ok {
143-
metadata["labels"] = make(map[string]string)
144-
}
145-
labels := metadata["labels"].(map[string]string)
146-
labels[appWrapperLabel] = aw.Name
147-
if len(toInject.Labels) > 0 {
148-
if err := utilmaps.HaveConflict(labels, toInject.Labels); err != nil {
149-
return podset.BadPodSetsUpdateError("labels", err)
150-
}
151-
labels = utilmaps.MergeKeepFirst(labels, toInject.Labels)
137+
// Labels
138+
if _, ok := metadata["labels"]; !ok {
139+
metadata["labels"] = make(map[string]string)
140+
}
141+
labels := metadata["labels"].(map[string]string)
142+
labels[appWrapperLabel] = aw.Name
143+
if len(toInject.Labels) > 0 {
144+
if err := utilmaps.HaveConflict(labels, toInject.Labels); err != nil {
145+
return podset.BadPodSetsUpdateError("labels", err)
152146
}
153-
metadata["labels"] = labels
147+
labels = utilmaps.MergeKeepFirst(labels, toInject.Labels)
148+
}
149+
metadata["labels"] = labels
154150

155-
spec := p["spec"].(map[string]interface{}) // AppWrapper ValidatingAC ensures this succeeds
151+
spec := p["spec"].(map[string]interface{}) // AppWrapper ValidatingAC ensures this succeeds
156152

157-
// NodeSelectors
158-
if len(toInject.NodeSelector) > 0 {
159-
if _, ok := spec["nodeSelector"]; !ok {
160-
spec["nodeSelector"] = make(map[string]string)
161-
}
162-
selector := spec["nodeSelector"].(map[string]string)
163-
if err := utilmaps.HaveConflict(selector, toInject.NodeSelector); err != nil {
153+
// NodeSelectors
154+
if len(toInject.NodeSelector) > 0 {
155+
if selectors, ok := metadata["nodeSelector"]; ok {
156+
metadata["nodeSelector"] = maps.Clone(toInject.NodeSelector)
157+
} else {
158+
if err := utilmaps.HaveConflict(selectors.(map[string]string), toInject.NodeSelector); err != nil {
164159
return podset.BadPodSetsUpdateError("nodeSelector", err)
165160
}
166-
spec["nodeSelector"] = utilmaps.MergeKeepFirst(selector, toInject.NodeSelector)
161+
metadata["nodeSelector"] = utilmaps.MergeKeepFirst(metadata["nodeSelector"].(map[string]string), toInject.NodeSelector)
167162
}
163+
}
168164

169-
// Tolerations
170-
if len(toInject.Tolerations) > 0 {
171-
if _, ok := spec["tolerations"]; !ok {
172-
spec["tolerations"] = []interface{}{}
173-
}
174-
tolerations := spec["tolerations"].([]interface{})
175-
for _, addition := range toInject.Tolerations {
176-
bytes, err := json.Marshal(addition)
177-
if err != nil {
178-
return err
179-
}
180-
tmp := &unstructured.Unstructured{}
181-
if _, _, err := unstructured.UnstructuredJSONScheme.Decode(bytes, nil, tmp); err != nil {
182-
return err
183-
}
184-
tolerations = append(tolerations, tmp.UnstructuredContent())
185-
}
165+
// Tolerations
166+
if len(toInject.Tolerations) > 0 {
167+
if _, ok := spec["tolerations"]; !ok {
168+
spec["tolerations"] = []interface{}{}
169+
}
170+
tolerations := spec["tolerations"].([]interface{})
171+
for _, addition := range toInject.Tolerations {
172+
tolerations = append(tolerations, addition)
186173
}
174+
spec["tolerations"] = tolerations
187175
}
188176
}
189177

@@ -217,56 +205,44 @@ func (aw *AppWrapper) RestorePodSetsInfo(podSetsInfo []podset.PodSetInfo) bool {
217205
PODSETLOOP:
218206
for _, podSet := range component.PodSets {
219207
podSetsInfoIndex += 1
220-
if podSetsInfoIndex <= len(podSetsInfo) {
221-
toRestore := podSetsInfo[podSetsInfoIndex-1]
222-
parts := strings.Split(podSet.Path, ".")
223-
p := obj.UnstructuredContent()
224-
var ok bool
225-
for i := 1; i < len(parts); i++ {
226-
p, ok = p[parts[i]].(map[string]interface{})
227-
if !ok {
228-
continue PODSETLOOP // Kueue provides no way to indicate that RestorePodSetsInfo hit an error
229-
}
230-
}
231-
objChanged = true // We injected a label into every PodTemplateSpec, so we always have something to remove
208+
if podSetsInfoIndex > len(podSetsInfo) {
209+
continue
210+
}
211+
toRestore := podSetsInfo[podSetsInfoIndex-1]
212+
p := getSubObject(obj.UnstructuredContent(), podSet.Path)
213+
if p == nil {
214+
continue PODSETLOOP // Kueue provides no way to indicate that RestorePodSetsInfo hit an error
215+
}
216+
objChanged = true // We injected an AppWrapper label into every PodTemplateSpec, so we always have something to remove
232217

233-
metadata := p["metadata"].(map[string]interface{}) // Must be non-nil, because we injected a label
234-
if len(toRestore.Annotations) > 0 {
235-
metadata["annotations"] = maps.Clone(toRestore.Annotations)
236-
} else {
237-
delete(metadata, "annotations")
238-
}
218+
metadata := p["metadata"].(map[string]interface{}) // Must be non-nil, because we injected a label
219+
if len(toRestore.Annotations) > 0 {
220+
metadata["annotations"] = maps.Clone(toRestore.Annotations)
221+
} else {
222+
delete(metadata, "annotations")
223+
}
239224

240-
if len(toRestore.Labels) > 0 {
241-
metadata["labels"] = maps.Clone(toRestore.Labels)
242-
} else {
243-
delete(metadata, "labels")
244-
}
225+
if len(toRestore.Labels) > 0 {
226+
metadata["labels"] = maps.Clone(toRestore.Labels)
227+
} else {
228+
delete(metadata, "labels")
229+
}
245230

246-
spec := p["spec"].(map[string]interface{})
247-
if len(toRestore.Labels) > 0 {
248-
spec["nodeSelector"] = maps.Clone(toRestore.NodeSelector)
249-
} else {
250-
delete(spec, "nodeSelector")
251-
}
231+
spec := p["spec"].(map[string]interface{})
232+
if len(toRestore.NodeSelector) > 0 {
233+
spec["nodeSelector"] = maps.Clone(toRestore.NodeSelector)
234+
} else {
235+
delete(spec, "nodeSelector")
236+
}
252237

253-
if len(toRestore.Tolerations) > 0 {
254-
tolerations := make([]interface{}, len(toRestore.Tolerations))
255-
for idx, tol := range toRestore.Tolerations {
256-
bytes, err := json.Marshal(tol)
257-
if err != nil {
258-
continue // should be impossible
259-
}
260-
tmp := &unstructured.Unstructured{}
261-
if _, _, err := unstructured.UnstructuredJSONScheme.Decode(bytes, nil, tmp); err != nil {
262-
continue // should be impossible
263-
}
264-
tolerations[idx] = tmp.UnstructuredContent()
265-
}
266-
spec["tolerations"] = tolerations
267-
} else {
268-
delete(spec, "tolerations")
238+
if len(toRestore.Tolerations) > 0 {
239+
tolerations := make([]interface{}, len(toRestore.Tolerations))
240+
for idx, tol := range toRestore.Tolerations {
241+
tolerations[idx] = tol
269242
}
243+
spec["tolerations"] = tolerations
244+
} else {
245+
delete(spec, "tolerations")
270246
}
271247
}
272248

0 commit comments

Comments
 (0)