volcano.sh/volcano@v1.9.0/test/e2e/util/configmap.go (about)

     1  package util
     2  
     3  import (
     4  	"context"
     5  	"strings"
     6  	"time"
     7  
     8  	"github.com/onsi/gomega"
     9  
    10  	v1 "k8s.io/api/core/v1"
    11  	metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
    12  )
    13  
    14  type ConfigMapCase struct {
    15  	NameSpace string
    16  	Name      string // configmap.name
    17  
    18  	startTs  time.Time // start timestamp
    19  	undoData map[string]string
    20  	ocm      *v1.ConfigMap
    21  }
    22  
    23  func NewConfigMapCase(ns, name string) *ConfigMapCase {
    24  	return &ConfigMapCase{
    25  		NameSpace: ns,
    26  		Name:      name,
    27  
    28  		undoData: make(map[string]string),
    29  	}
    30  }
    31  
    32  // ChangeBy call fn and update configmap by changed
    33  func (c *ConfigMapCase) ChangeBy(fn func(data map[string]string) (changed bool, changedBefore map[string]string)) error {
    34  	if c.ocm == nil {
    35  		cm, err := KubeClient.CoreV1().ConfigMaps(c.NameSpace).Get(context.TODO(), c.Name, metav1.GetOptions{})
    36  		gomega.Expect(err).NotTo(gomega.HaveOccurred())
    37  		c.ocm = cm
    38  	}
    39  	if changed, changedBefore := fn(c.ocm.Data); changed {
    40  		time.Sleep(time.Second) // wait last configmap-change done completely
    41  		cm, err := KubeClient.CoreV1().ConfigMaps(c.NameSpace).Update(context.TODO(), c.ocm, metav1.UpdateOptions{})
    42  		gomega.Expect(err).NotTo(gomega.HaveOccurred())
    43  		c.ocm, c.undoData = cm, changedBefore
    44  
    45  		// add pod/volcano-scheduler.annotation to update Mounted-ConfigMaps immediately
    46  		schedulerPods, err := KubeClient.CoreV1().Pods("volcano-system").List(context.TODO(), metav1.ListOptions{LabelSelector: "app=volcano-scheduler"})
    47  		gomega.Expect(err).NotTo(gomega.HaveOccurred())
    48  		for _, scheduler := range schedulerPods.Items {
    49  			if !strings.Contains(scheduler.Name, "scheduler") {
    50  				continue
    51  			}
    52  			if scheduler.Annotations == nil {
    53  				scheduler.Annotations = make(map[string]string)
    54  			}
    55  			scheduler.Annotations["refreshts"] = time.Now().Format("060102150405.000")
    56  			_, err = KubeClient.CoreV1().Pods("volcano-system").Update(context.TODO(), &scheduler, metav1.UpdateOptions{})
    57  			gomega.Expect(err).NotTo(gomega.HaveOccurred())
    58  		}
    59  		c.startTs = time.Now()
    60  	}
    61  	return nil
    62  }
    63  
    64  // UndoChanged restore configmap if exist undoData
    65  func (c *ConfigMapCase) UndoChanged() error {
    66  	if len(c.undoData) == 0 {
    67  		return nil
    68  	}
    69  	for filename, old := range c.undoData {
    70  		c.ocm.Data[filename] = old
    71  	}
    72  	atLeast := time.Second // at least 1s wait between 2 configmap-change
    73  	if dur := time.Now().Sub(c.startTs); dur < atLeast {
    74  		time.Sleep(atLeast - dur)
    75  	}
    76  	cm, err := KubeClient.CoreV1().ConfigMaps(c.NameSpace).Update(context.TODO(), c.ocm, metav1.UpdateOptions{})
    77  	gomega.Expect(err).NotTo(gomega.HaveOccurred())
    78  	c.ocm = cm
    79  
    80  	// add pod/volcano-scheduler.annotation to update Mounted-ConfigMaps immediately
    81  	schedulerPods, err := KubeClient.CoreV1().Pods("volcano-system").List(context.TODO(), metav1.ListOptions{LabelSelector: "app=volcano-scheduler"})
    82  	gomega.Expect(err).NotTo(gomega.HaveOccurred())
    83  	for _, scheduler := range schedulerPods.Items {
    84  		if !strings.HasPrefix(scheduler.Name, "volcano-scheduler") {
    85  			continue
    86  		}
    87  		scheduler.Annotations["refreshts"] = time.Now().Format("060102150405.000")
    88  		_, err = KubeClient.CoreV1().Pods("volcano-system").Update(context.TODO(), &scheduler, metav1.UpdateOptions{})
    89  		gomega.Expect(err).NotTo(gomega.HaveOccurred())
    90  	}
    91  	return nil
    92  }
    93  
    94  // SchedulerConfiguration defines the configuration of scheduler.
    95  type SchedulerConfiguration struct {
    96  	// Actions defines the actions list of scheduler in order
    97  	Actions string `yaml:"actions"`
    98  	// Tiers defines plugins in different tiers
    99  	Tiers []Tier `yaml:"tiers,omitempty"`
   100  	// Configurations is configuration for actions
   101  	Configurations []Configuration `yaml:"configurations,omitempty"`
   102  }
   103  
   104  // Tier defines plugin tier
   105  type Tier struct {
   106  	Plugins []PluginOption `yaml:"plugins,omitempty"`
   107  }
   108  
   109  func (t Tier) ContainsPlugin(name string) bool {
   110  	return t.GetPluginIdxOf(name) >= 0
   111  }
   112  
   113  func (t Tier) GetPluginIdxOf(name string) int {
   114  	for idx, p := range t.Plugins {
   115  		if p.Name == name {
   116  			return idx
   117  		}
   118  	}
   119  	return -1
   120  }
   121  
   122  // Configuration is configuration of action
   123  type Configuration struct {
   124  	// Name is name of action
   125  	Name string `yaml:"name"`
   126  	// Arguments defines the different arguments that can be given to specified action
   127  	Arguments map[string]string `yaml:"arguments,omitempty"`
   128  }
   129  
   130  // PluginOption defines the options of plugin
   131  type PluginOption struct {
   132  	// The name of Plugin
   133  	Name string `yaml:"name"`
   134  	// EnabledJobOrder defines whether jobOrderFn is enabled
   135  	EnabledJobOrder *bool `yaml:"enableJobOrder,omitempty"`
   136  	// EnabledHierachy defines whether hierarchical sharing is enabled
   137  	EnabledHierarchy *bool `yaml:"enableHierarchy,omitempty"`
   138  	// EnabledJobReady defines whether jobReadyFn is enabled
   139  	EnabledJobReady *bool `yaml:"enableJobReady,omitempty"`
   140  	// EnabledJobPipelined defines whether jobPipelinedFn is enabled
   141  	EnabledJobPipelined *bool `yaml:"enableJobPipelined,omitempty"`
   142  	// EnabledTaskOrder defines whether taskOrderFn is enabled
   143  	EnabledTaskOrder *bool `yaml:"enableTaskOrder,omitempty"`
   144  	// EnabledPreemptable defines whether preemptableFn is enabled
   145  	EnabledPreemptable *bool `yaml:"enablePreemptable,omitempty"`
   146  	// EnabledReclaimable defines whether reclaimableFn is enabled
   147  	EnabledReclaimable *bool `yaml:"enableReclaimable,omitempty"`
   148  	// EnabledQueueOrder defines whether queueOrderFn is enabled
   149  	EnabledQueueOrder *bool `yaml:"enableQueueOrder,omitempty"`
   150  	// EnabledPredicate defines whether predicateFn is enabled
   151  	EnabledClusterOrder *bool `yaml:"EnabledClusterOrder,omitempty"`
   152  	// EnableClusterOrder defines whether clusterOrderFn is enabled
   153  	EnabledPredicate *bool `yaml:"enablePredicate,omitempty"`
   154  	// EnabledBestNode defines whether bestNodeFn is enabled
   155  	EnabledBestNode *bool `yaml:"enableBestNode,omitempty"`
   156  	// EnabledNodeOrder defines whether NodeOrderFn is enabled
   157  	EnabledNodeOrder *bool `yaml:"enableNodeOrder,omitempty"`
   158  	// EnabledTargetJob defines whether targetJobFn is enabled
   159  	EnabledTargetJob *bool `yaml:"enableTargetJob,omitempty"`
   160  	// EnabledReservedNodes defines whether reservedNodesFn is enabled
   161  	EnabledReservedNodes *bool `yaml:"enableReservedNodes,omitempty"`
   162  	// EnabledJobEnqueued defines whether jobEnqueuedFn is enabled
   163  	EnabledJobEnqueued *bool `yaml:"enableJobEnqueued,omitempty"`
   164  	// EnabledVictim defines whether victimsFn is enabled
   165  	EnabledVictim *bool `yaml:"enabledVictim,omitempty"`
   166  	// EnabledJobStarving defines whether jobStarvingFn is enabled
   167  	EnabledJobStarving *bool `yaml:"enableJobStarving,omitempty"`
   168  	// Arguments defines the different arguments that can be given to different plugins
   169  	Arguments map[string]string `yaml:"arguments,omitempty"`
   170  }