Skip to content

Commit ff6441b

Browse files
authored
More container fields for SuggestionConfig (#2000)
* More container fields for SuggestionConfig * Inline corev1.Container into SuggestionConfig * Set default value for suggestion container name * Append suggestion volume and port only if not present * Deep-Copy base suggestion container * Check for suggestion container port number as well * Prohibit suggestion port to be set in suggestion config
1 parent 55e6e34 commit ff6441b

File tree

5 files changed

+89
-43
lines changed

5 files changed

+89
-43
lines changed

pkg/controller.v1beta1/suggestion/composer/composer.go

Lines changed: 62 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -76,6 +76,11 @@ func (g *General) DesiredDeployment(s *suggestionsv1beta1.Suggestion) (*appsv1.D
7676
if err != nil {
7777
return nil, err
7878
}
79+
if containsContainerPortWithName(suggestionConfigData.Ports, consts.DefaultSuggestionPortName) ||
80+
containsContainerPort(suggestionConfigData.Ports, consts.DefaultSuggestionPort) {
81+
return nil, fmt.Errorf("invalid suggestion config: a port with name %q or number %d must not be specified",
82+
consts.DefaultSuggestionPortName, consts.DefaultSuggestionPort)
83+
}
7984

8085
// If early stopping is used, get the config data.
8186
earlyStoppingConfigData := katibconfig.EarlyStoppingConfig{}
@@ -181,21 +186,27 @@ func (g *General) desiredContainers(s *suggestionsv1beta1.Suggestion,
181186
suggestionConfigData katibconfig.SuggestionConfig,
182187
earlyStoppingConfigData katibconfig.EarlyStoppingConfig) []corev1.Container {
183188

184-
containers := []corev1.Container{}
185-
suggestionContainer := corev1.Container{
186-
Name: consts.ContainerSuggestion,
187-
Image: suggestionConfigData.Image,
188-
ImagePullPolicy: suggestionConfigData.ImagePullPolicy,
189-
Ports: []corev1.ContainerPort{
190-
{
191-
Name: consts.DefaultSuggestionPortName,
192-
ContainerPort: consts.DefaultSuggestionPort,
193-
},
194-
},
195-
Resources: suggestionConfigData.Resource,
189+
var (
190+
containers []corev1.Container
191+
suggestionContainer corev1.Container
192+
)
193+
194+
suggestionConfigData.Container.DeepCopyInto(&suggestionContainer)
195+
196+
// Assign default values for suggestionContainer fields that are not set via
197+
// the suggestion config.
198+
199+
if suggestionContainer.Name == "" {
200+
suggestionContainer.Name = consts.ContainerSuggestion
196201
}
197202

198-
if viper.GetBool(consts.ConfigEnableGRPCProbeInSuggestion) {
203+
suggestionPort := corev1.ContainerPort{
204+
Name: consts.DefaultSuggestionPortName,
205+
ContainerPort: consts.DefaultSuggestionPort,
206+
}
207+
suggestionContainer.Ports = append(suggestionContainer.Ports, suggestionPort)
208+
209+
if viper.GetBool(consts.ConfigEnableGRPCProbeInSuggestion) && suggestionContainer.ReadinessProbe == nil {
199210
suggestionContainer.ReadinessProbe = &corev1.Probe{
200211
ProbeHandler: corev1.ProbeHandler{
201212
Exec: &corev1.ExecAction{
@@ -209,6 +220,8 @@ func (g *General) desiredContainers(s *suggestionsv1beta1.Suggestion,
209220
InitialDelaySeconds: defaultInitialDelaySeconds,
210221
PeriodSeconds: defaultPeriodForReady,
211222
}
223+
}
224+
if viper.GetBool(consts.ConfigEnableGRPCProbeInSuggestion) && suggestionContainer.LivenessProbe == nil {
212225
suggestionContainer.LivenessProbe = &corev1.Probe{
213226
ProbeHandler: corev1.ProbeHandler{
214227
Exec: &corev1.ExecAction{
@@ -226,15 +239,14 @@ func (g *General) desiredContainers(s *suggestionsv1beta1.Suggestion,
226239
}
227240
}
228241

229-
// Attach volume mounts to the suggestion container if ResumePolicy = FromVolume
230-
if s.Spec.ResumePolicy == experimentsv1beta1.FromVolume {
231-
suggestionContainer.VolumeMounts = []corev1.VolumeMount{
232-
{
233-
Name: consts.ContainerSuggestionVolumeName,
234-
MountPath: suggestionConfigData.VolumeMountPath,
235-
},
242+
if s.Spec.ResumePolicy == experimentsv1beta1.FromVolume && !containsVolumeMountWithName(suggestionContainer.VolumeMounts, consts.ContainerSuggestionVolumeName) {
243+
suggestionVolume := corev1.VolumeMount{
244+
Name: consts.ContainerSuggestionVolumeName,
245+
MountPath: suggestionConfigData.VolumeMountPath,
236246
}
247+
suggestionContainer.VolumeMounts = append(suggestionContainer.VolumeMounts, suggestionVolume)
237248
}
249+
238250
containers = append(containers, suggestionContainer)
239251

240252
if s.Spec.EarlyStopping != nil && s.Spec.EarlyStopping.AlgorithmName != "" {
@@ -256,6 +268,36 @@ func (g *General) desiredContainers(s *suggestionsv1beta1.Suggestion,
256268
return containers
257269
}
258270

271+
func containsVolumeMountWithName(volumeMounts []corev1.VolumeMount, name string) bool {
272+
for i := range volumeMounts {
273+
if volumeMounts[i].Name == name {
274+
return true
275+
}
276+
}
277+
278+
return false
279+
}
280+
281+
func containsContainerPortWithName(ports []corev1.ContainerPort, name string) bool {
282+
for i := range ports {
283+
if ports[i].Name == name {
284+
return true
285+
}
286+
}
287+
288+
return false
289+
}
290+
291+
func containsContainerPort(ports []corev1.ContainerPort, port int32) bool {
292+
for i := range ports {
293+
if ports[i].ContainerPort == port {
294+
return true
295+
}
296+
}
297+
298+
return false
299+
}
300+
259301
// DesiredVolume returns desired PVC and PV for Suggestion.
260302
// If PV doesn't exist in Katib config return nil for PV.
261303
func (g *General) DesiredVolume(s *suggestionsv1beta1.Suggestion) (*corev1.PersistentVolumeClaim, *corev1.PersistentVolume, error) {

pkg/controller.v1beta1/suggestion/composer/composer_test.go

Lines changed: 14 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -646,18 +646,20 @@ func newFakeSuggestionConfig() katibconfig.SuggestionConfig {
646646
diskQ, _ := resource.ParseQuantity(disk)
647647

648648
return katibconfig.SuggestionConfig{
649-
Image: image,
650-
ImagePullPolicy: imagePullPolicy,
651-
Resource: corev1.ResourceRequirements{
652-
Limits: corev1.ResourceList{
653-
corev1.ResourceCPU: cpuQ,
654-
corev1.ResourceMemory: memoryQ,
655-
corev1.ResourceEphemeralStorage: diskQ,
656-
},
657-
Requests: corev1.ResourceList{
658-
corev1.ResourceCPU: cpuQ,
659-
corev1.ResourceMemory: memoryQ,
660-
corev1.ResourceEphemeralStorage: diskQ,
649+
Container: corev1.Container{
650+
Image: image,
651+
ImagePullPolicy: imagePullPolicy,
652+
Resources: corev1.ResourceRequirements{
653+
Limits: corev1.ResourceList{
654+
corev1.ResourceCPU: cpuQ,
655+
corev1.ResourceMemory: memoryQ,
656+
corev1.ResourceEphemeralStorage: diskQ,
657+
},
658+
Requests: corev1.ResourceList{
659+
corev1.ResourceCPU: cpuQ,
660+
corev1.ResourceMemory: memoryQ,
661+
corev1.ResourceEphemeralStorage: diskQ,
662+
},
661663
},
662664
},
663665
ServiceAccountName: serviceAccount,

pkg/controller.v1beta1/suggestion/suggestion_controller_test.go

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -435,7 +435,9 @@ func newKatibConfigMapInstance() *corev1.ConfigMap {
435435
// Create suggestion config
436436
suggestionConfig := map[string]katibconfig.SuggestionConfig{
437437
"random": {
438-
Image: suggestionImage,
438+
Container: corev1.Container{
439+
Image: suggestionImage,
440+
},
439441
},
440442
}
441443
bSuggestionConfig, _ := json.Marshal(suggestionConfig)

pkg/util/v1beta1/katibconfig/config.go

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -34,9 +34,7 @@ import (
3434

3535
// SuggestionConfig is the JSON suggestion structure in Katib config.
3636
type SuggestionConfig struct {
37-
Image string `json:"image"`
38-
ImagePullPolicy corev1.PullPolicy `json:"imagePullPolicy,omitempty"`
39-
Resource corev1.ResourceRequirements `json:"resources,omitempty"`
37+
corev1.Container `json:",inline"`
4038
ServiceAccountName string `json:"serviceAccountName,omitempty"`
4139
VolumeMountPath string `json:"volumeMountPath,omitempty"`
4240
PersistentVolumeClaimSpec corev1.PersistentVolumeClaimSpec `json:"persistentVolumeClaimSpec,omitempty"`
@@ -99,7 +97,7 @@ func GetSuggestionConfigData(algorithmName string, client client.Client) (Sugges
9997
suggestionConfigData.ImagePullPolicy = setImagePullPolicy(suggestionConfigData.ImagePullPolicy)
10098

10199
// Set resource requirements for suggestion
102-
suggestionConfigData.Resource = setResourceRequirements(suggestionConfigData.Resource)
100+
suggestionConfigData.Resources = setResourceRequirements(suggestionConfigData.Resources)
103101

104102
// Set default suggestion container volume mount path
105103
if suggestionConfigData.VolumeMountPath == "" {

pkg/util/v1beta1/katibconfig/config_test.go

Lines changed: 8 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -54,13 +54,13 @@ func TestGetSuggestionConfigData(t *testing.T) {
5454
katibConfig: func() *katibConfig {
5555
kc := &katibConfig{suggestion: map[string]*SuggestionConfig{testAlgorithmName: newFakeSuggestionConfig()}}
5656
kc.suggestion[testAlgorithmName].ImagePullPolicy = corev1.PullAlways
57-
kc.suggestion[testAlgorithmName].Resource = *newFakeCustomResourceRequirements()
57+
kc.suggestion[testAlgorithmName].Resources = *newFakeCustomResourceRequirements()
5858
return kc
5959
}(),
6060
expected: func() *SuggestionConfig {
6161
c := newFakeSuggestionConfig()
6262
c.ImagePullPolicy = corev1.PullAlways
63-
c.Resource = *newFakeCustomResourceRequirements()
63+
c.Resources = *newFakeCustomResourceRequirements()
6464
return c
6565
}(),
6666
inputAlgorithmName: testAlgorithmName,
@@ -107,7 +107,7 @@ func TestGetSuggestionConfigData(t *testing.T) {
107107
testDescription: "GetSuggestionConfigData sets resource.requests and resource.limits for the suggestion service",
108108
katibConfig: func() *katibConfig {
109109
kc := &katibConfig{suggestion: map[string]*SuggestionConfig{testAlgorithmName: newFakeSuggestionConfig()}}
110-
kc.suggestion[testAlgorithmName].Resource = corev1.ResourceRequirements{}
110+
kc.suggestion[testAlgorithmName].Resources = corev1.ResourceRequirements{}
111111
return kc
112112
}(),
113113
expected: newFakeSuggestionConfig(),
@@ -402,9 +402,11 @@ func newFakeSuggestionConfig() *SuggestionConfig {
402402
defaultVolumeStorage, _ := resource.ParseQuantity(consts.DefaultSuggestionVolumeStorage)
403403

404404
return &SuggestionConfig{
405-
Image: "suggestion-image",
406-
ImagePullPolicy: consts.DefaultImagePullPolicy,
407-
Resource: *setFakeResourceRequirements(),
405+
Container: corev1.Container{
406+
Image: "suggestion-image",
407+
ImagePullPolicy: consts.DefaultImagePullPolicy,
408+
Resources: *setFakeResourceRequirements(),
409+
},
408410
VolumeMountPath: consts.DefaultContainerSuggestionVolumeMountPath,
409411
PersistentVolumeClaimSpec: corev1.PersistentVolumeClaimSpec{
410412
AccessModes: []corev1.PersistentVolumeAccessMode{

0 commit comments

Comments
 (0)