Skip to content

Commit

Permalink
fix: K8s version change transformer was not being run sometimes becau…
Browse files Browse the repository at this point in the history
…se Parameterizer was running first (#1165)

feat: Added a new feature to sort transformers based on a label
"move2kube.konveyor.io/sort-order" specified in the transformer.yaml.
This is only the initial sorted order in which transformers are run
and does not affect dependency related stuff like MandatoryPassThrough.

Signed-off-by: Harikrishnan Balagopal <harikrishmenon@gmail.com>
  • Loading branch information
HarikrishnanBalagopal committed Mar 25, 2024
1 parent 7383e91 commit 0c79d6d
Show file tree
Hide file tree
Showing 4 changed files with 56 additions and 1 deletion.
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ metadata:
name: KubernetesVersionChanger
labels:
move2kube.konveyor.io/built-in: true
move2kube.konveyor.io/sort-order: 9999
spec:
class: "KubernetesVersionChanger"
directoryDetect:
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ metadata:
name: Parameterizer
labels:
move2kube.konveyor.io/built-in: true
move2kube.konveyor.io/sort-order: 10000
spec:
class: "Parameterizer"
directoryDetect:
Expand Down
28 changes: 28 additions & 0 deletions common/utils.go
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,34 @@ import (
core "k8s.io/kubernetes/pkg/apis/core"
)

// sorting

// Sortable is an implementation of the sort.Interface interface.
// This is useful when you want to sort one slice using another slice.
type Sortable[T any] struct {
Xs []T
Ys []int
}

// Len is the number of elements in the collection.
func (s *Sortable[T]) Len() int {
return len(s.Xs)
}

// Less reports whether the element with index i
// must sort before the element with index j.
func (s *Sortable[T]) Less(i, j int) bool {
return s.Ys[i] < s.Ys[j]
}

// Swap swaps the elements with indexes i and j.
func (s *Sortable[T]) Swap(i, j int) {
s.Xs[i], s.Xs[j] = s.Xs[j], s.Xs[i]
s.Ys[i], s.Ys[j] = s.Ys[j], s.Ys[i]
}

// sorting

// LookupEnv looks for a environment variable in a list of environment variables
func LookupEnv(envNameToLookup string, envList []core.EnvVar) (core.EnvVar, bool) {
for _, env := range envList {
Expand Down
27 changes: 26 additions & 1 deletion transformer/transformer.go
Original file line number Diff line number Diff line change
Expand Up @@ -76,6 +76,8 @@ const (
DEFAULT_SELECTED_LABEL = types.GroupName + "/default-selected"
// CONTAINER_BASED_LABEL is a label that indicates that the transformer needs to spawn containers to run.
CONTAINER_BASED_LABEL = types.GroupName + "/container-based"
// SORT_ORDER_LABEL is a label that is used while sorting the list of all transformers.
SORT_ORDER_LABEL = types.GroupName + "/sort-order"
)

var (
Expand Down Expand Up @@ -232,7 +234,8 @@ func InitTransformers(transformerYamlPaths map[string]string, selector labels.Se
deselectedTransformers[transformerName] = transformerYamlPaths[transformerName]
}
}
for _, selectedTransformerName := range selectedTransformerNames {
transformerSortOrders := []int{}
for currSortOrder, selectedTransformerName := range selectedTransformerNames {
transformerConfig, ok := transformerConfigs[selectedTransformerName]
if !ok {
logrus.Errorf("failed to find the transformer with the name: '%s'", selectedTransformerName)
Expand Down Expand Up @@ -284,12 +287,34 @@ func InitTransformers(transformerYamlPaths map[string]string, selector labels.Se
continue
}
transformers = append(transformers, transformer)
// for sorting later on
newSortOrder := currSortOrder
if s, ok := transformerConfig.ObjectMeta.Labels[SORT_ORDER_LABEL]; ok {
if x, err := cast.ToIntE(s); err != nil {
logrus.Errorf(
"Using %d as the sort order since the one specified in the transformer.yaml is not a valid integer. Actual: '%s' Error: %q",
currSortOrder, s, err,
)
} else {
logrus.Debugf("using new sort order: %d", x)
newSortOrder = x
}
}
transformerSortOrders = append(transformerSortOrders, newSortOrder)
// for sorting later on
transformerMap[selectedTransformerName] = transformer
if transformerConfig.Spec.InvokedByDefault.Enabled {
invokedByDefaultTransformers = append(invokedByDefaultTransformers, transformer)
}
}
initialized = true
if len(transformerSortOrders) != len(transformers) {
panic("expected transformers and transformerSortOrders to have the same length")
}
logrus.Debugf("before sorting the transformers list, transformerSortOrders: %+v transformers: %+v", transformerSortOrders, transformers)
sortable := &common.Sortable[Transformer]{Xs: transformers, Ys: transformerSortOrders}
sort.Stable(sortable)
logrus.Debugf("after sorting the transformers list, transformerSortOrders: %+v transformers: %+v", transformerSortOrders, transformers)
return deselectedTransformers, nil
}

Expand Down

0 comments on commit 0c79d6d

Please sign in to comment.