k8s.io/perf-tests/clusterloader2@v0.0.0-20240304094227-64bdb12da87e/api/types.go (about)

     1  /*
     2  Copyright 2018 The Kubernetes Authors.
     3  
     4  Licensed under the Apache License, Version 2.0 (the "License");
     5  you may not use this file except in compliance with the License.
     6  You may obtain a copy of the License at
     7  
     8      http://www.apache.org/licenses/LICENSE-2.0
     9  
    10  Unless required by applicable law or agreed to in writing, software
    11  distributed under the License is distributed on an "AS IS" BASIS,
    12  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    13  See the License for the specific language governing permissions and
    14  limitations under the License.
    15  */
    16  
    17  package api
    18  
    19  import (
    20  	"time"
    21  
    22  	metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
    23  	"k8s.io/apimachinery/pkg/util/sets"
    24  )
    25  
    26  // TestSuite defines list of test scenarios to be run.
    27  type TestSuite []TestScenario
    28  
    29  // TestScenario defines customized test to be run.
    30  type TestScenario struct {
    31  	// Identifier is a unique test scenario name across test suite.
    32  	Identifier string `json:"identifier"`
    33  	// ConfigPath defines path to the file containing a single Config definition.
    34  	ConfigPath string `json:"configPath"`
    35  	// OverridePaths defines what override files should be applied
    36  	// to the config specified by the ConfigPath. This supersedes the global
    37  	// config provided by ClusterLoaderConfig.
    38  	OverridePaths []string `json:"overridePaths"`
    39  }
    40  
    41  // Config is a structure that represents configuration
    42  // for a single test scenario.
    43  type Config struct {
    44  	// Name of the test case.
    45  	Name string `json:"name"`
    46  	// TODO(#1696): Clean up after removing automanagedNamespaces
    47  	AutomanagedNamespaces int32 `json:"automanagedNamespaces,omitempty"`
    48  	// Namespace is a structure for namespace configuration.
    49  	Namespace NamespaceConfig `json:"namespace"`
    50  	// Steps is a sequence of test steps executed in serial.
    51  	Steps []*Step `json:"steps"`
    52  	// TuningSets is a collection of tuning sets that can be used by steps.
    53  	TuningSets []*TuningSet `json:"tuningSets"`
    54  	// ChaosMonkey is a config for simulated component failures.
    55  	ChaosMonkey ChaosMonkeyConfig `json:"chaosMonkey"`
    56  }
    57  
    58  // Step represents a unit of work in ClusterLoader2. It can be either:
    59  // - a collection of measurements,
    60  // - a collection of phases,
    61  // - a module (sequence of steps).
    62  // Exactly one field (Phases or Measurements or Module) should be non-empty.
    63  type Step struct {
    64  	// Phases is a collection of declarative definitions of objects.
    65  	// Phases will be executed in parallel.
    66  	Phases []*Phase `json:"phases"`
    67  	// Measurements is a collection of parallel measurement calls.
    68  	Measurements []*Measurement `json:"measurements"`
    69  	// Module points to a CL2 module defined in a separate file.
    70  	Module ModuleRef `json:"module"`
    71  	// Name is an optional name for given step. If name is set the step execution
    72  	// time will be measured and the step will be reported at the end of the test.
    73  	// The name is ignored if the step is of type 'Module'.
    74  	Name string `json:"name"`
    75  }
    76  
    77  // ModuleRef is a structure that points to a Module defined in a separate file.
    78  type ModuleRef struct {
    79  	// Path is the path to the filename with the module template.
    80  	Path string `json:"path"`
    81  	// Params specifies template parameters to be substituted inside the template.
    82  	Params map[string]interface{} `json:"params"`
    83  }
    84  
    85  // Module is a structure with the definition of a CL2 module. Conceptually, a
    86  // module is a sequence of steps.
    87  type Module struct {
    88  	// Steps is the list of steps composing the module. Steps are executed
    89  	// serially.
    90  	Steps []*Step `json:"steps"`
    91  }
    92  
    93  // Phase is a structure that declaratively defines state of objects.
    94  // In a given namespace range (or cluster scope if no range is specified)
    95  // it defines the number and the configuration of managed objects.
    96  type Phase struct {
    97  	// NamespaceRange defines the range of generated namespaces in which objects
    98  	// should be reconciled.
    99  	// If null, objects are assumed to be cluster scoped.
   100  	// Note: Only one of NamespaceList and NamespaceRange should be set
   101  	NamespaceRange *NamespaceRange `json:"namespaceRange"`
   102  	// NamespaceList defines a list of namespaces in which objects
   103  	// should be reconciled. This is used for resources that should be forced
   104  	// into specific namespaces.
   105  	// If null, assumed to use NamespaceRange.
   106  	// Note: Only one of NamespaceList and NamespaceRange should be set
   107  	NamespaceList []string `json:"namespaceList"`
   108  	// ReplicasPerNamespace is a number of instances of a given object
   109  	// to exist in each of referenced namespaces.
   110  	ReplicasPerNamespace int32 `json:"replicasPerNamespace"`
   111  	// TuningSet is the name of TuningSet to be used.
   112  	TuningSet string `json:"tuningSet"`
   113  	// ObjectBundle declaratively defines a set of objects.
   114  	// For every specified namespace and for every required replica,
   115  	// these objects will be reconciled in serial.
   116  	ObjectBundle []*Object `json:"objectBundle"`
   117  }
   118  
   119  // Object is a structure that defines the object managed be the tests.
   120  type Object struct {
   121  	// Basename is a string from which names of objects will be created.
   122  	Basename string `json:"basename"`
   123  	// ObjectTemplatePath specifies the path to object definition.
   124  	ObjectTemplatePath string `json:"objectTemplatePath"`
   125  	// TemplateFillMap specifies for each placeholder what value should it be replaced with.
   126  	TemplateFillMap map[string]interface{} `json:"templateFillMap"`
   127  	// ListUnknownObjectOptions, if set, will result in listing objects that were
   128  	// not created directly via ClusterLoader2 before executing Phase. The main
   129  	// use case for that is deleting unknown objects using the Phase mechanism,
   130  	// e.g. deleting PVs that were created via StatefulSets leveraging all Phase
   131  	// functionalities, e.g. respecting given QPS, doing it in parallel with other
   132  	// Phases, etc.
   133  	ListUnknownObjectOptions *ListUnknownObjectOptions `json:"listUnknownObjectOptions"`
   134  }
   135  
   136  // ListUnknownObjectOptions struct specifies options for listing unknown objects.
   137  type ListUnknownObjectOptions struct {
   138  	LabelSelector *metav1.LabelSelector `json:"labelSelector"`
   139  }
   140  
   141  // NamespaceConfig defines namespace parameters.
   142  type NamespaceConfig struct {
   143  	// Number is a number of automanaged namespaces.
   144  	Number int32 `json:"number,omitempty"`
   145  	// NamePrefix is the name prefix of automanaged namespaces.
   146  	// It's optional, if set CL will use it, otherwise generate one with random string.
   147  	Prefix string `json:"prefix,omitempty"`
   148  	// DeleteStaleNamespaces specifies whether or not delete stale namespaces.
   149  	DeleteStaleNamespaces *bool `json:"deleteStaleNamespaces,omitempty"`
   150  	// DeleteAutomanangedNamespaces specifies whether or not delete namespaces after a test.
   151  	DeleteAutomanagedNamespaces *bool `json:"deleteAutomanagedNamespaces,omitempty"`
   152  	// EnableExistingNamespaces enables to use pre-created namespaces in a test.
   153  	EnableExistingNamespaces *bool `json:"enableExistingNamespaces,omitempty"`
   154  	// DeleteNamespaceTimeout controls a timeout for waiting until automanaged namespaces are deleted.
   155  	// Defaults to 10m, if not set.
   156  	DeleteNamespaceTimeout *Duration `json:"deleteNamespaceTimeout,omitempty"`
   157  }
   158  
   159  // NamespaceRange specifies the range of namespaces [Min, Max].
   160  type NamespaceRange struct {
   161  	// Min is the lower index of namespace range.
   162  	Min int32 `json:"min"`
   163  	// Max is the upper index of namespace range.
   164  	Max int32 `json:"max"`
   165  	// Basename defines the group of selected namespaces.
   166  	// All of the namespaces, with name "<Basename>-<i>"
   167  	// where <i> in [Min, Max], will be selected.
   168  	// If no Basename is specified, automanaged namespace is assumed.
   169  	Basename *string
   170  }
   171  
   172  // TuningSet defines the timing of the operations.
   173  // There is an initial delay, and then a way of choosing when to start each operation.
   174  // It is required to have exactly one of the load structure provided.
   175  type TuningSet struct {
   176  	// Name by which the TuningSet will be referenced.
   177  	Name string `json:"name"`
   178  	// InitialDelay specifies the waiting time before starting phase execution.
   179  	InitialDelay Duration `json:"initialDelay"`
   180  	// QPSLoad is a definition for QPSLoad tuning set.
   181  	QPSLoad *QPSLoad `json:"qpsLoad"`
   182  	// RandomizedLoad is a definition for RandomizedLoad tuning set.
   183  	RandomizedLoad *RandomizedLoad `json:"randomizedLoad"`
   184  	// SteppedLoad is a definition for SteppedLoad tuning set.
   185  	SteppedLoad *SteppedLoad `json:"steppedLoad"`
   186  	// TimeLimitedLoad is a definition for TimeLimitedLoad tuning set.
   187  	TimeLimitedLoad *TimeLimitedLoad `json:"timeLimitedLoad"`
   188  	// RandomizedTimeLimitedLoad is a definition for RandomizedTimeLimitedLoad tuning set.
   189  	RandomizedTimeLimitedLoad *RandomizedTimeLimitedLoad `json:"randomizedTimeLimitedLoad"`
   190  	// ParallelismLimitedLoad is a definition for ParallelismLimitedLoad tuning set.
   191  	ParallelismLimitedLoad *ParallelismLimitedLoad `json:"parallelismLimitedLoad"`
   192  	// GlobalQPSLoad is a definition for GlobalQPSLoad tuning set.
   193  	GlobalQPSLoad *GlobalQPSLoad `json:"globalQPSLoad"`
   194  }
   195  
   196  // MeasurementInstanceConfig is a structure that contains the Instance for wrapper measurements along with optional params.
   197  type MeasurementInstanceConfig struct {
   198  	// Identifier is a string that identifies a single instance of measurement within a wrapper measurement
   199  	Identifier string `json:"identifier"`
   200  	// Params is an optional map which is specific to the measurement instance defined above by the identifier.
   201  	// In case the Measurement level params also contain the same configs as defined in this, then while executing that
   202  	// particular Measurement Instance, the params defined here would be given higher priority.
   203  	Params map[string]interface{} `json:"params"`
   204  }
   205  
   206  // Measurement is a structure that defines the measurement method call.
   207  // This method call will either start or stop process of collecting specific data samples.
   208  type Measurement struct {
   209  	// Method is a name of a method registered in the ClusterLoader factory.
   210  	Method string `json:"method"`
   211  	// Params is a map of {name: value} pairs which will be passed to the measurement method - allowing for injection of arbitrary parameters to it.
   212  	Params map[string]interface{} `json:"params"`
   213  
   214  	// Exactly one of Identifier or Instances must be supplied.
   215  	// Identifier is for single measurements while Instances is for wrapper measurements.
   216  	// Identifier is a string that differentiates measurement instances of the same method.
   217  	Identifier string `json:"identifier"`
   218  	// MeasurementInstanceConfig contains the Identifier and Params of the measurement.
   219  	// It shouldn't be set when Identifier is set.
   220  	Instances []*MeasurementInstanceConfig
   221  }
   222  
   223  // QPSLoad starts one operation every 1/QPS seconds.
   224  type QPSLoad struct {
   225  	// QPS specifies requested qps.
   226  	QPS float64 `json:"qps"`
   227  }
   228  
   229  // RandomizedLoad says the time between operation starts is drawn uniformly at random
   230  // from the range [0, 2s/AverageQPS).
   231  type RandomizedLoad struct {
   232  	// AverageQPS specifies the expected average qps.
   233  	AverageQPS float64 `json:"averageQps"`
   234  }
   235  
   236  // SteppedLoad defines a load that starts a burst of
   237  // a given size every X seconds.
   238  type SteppedLoad struct {
   239  	// BurstSize specifies the qps peek.
   240  	BurstSize int32 `json:"burstSize"`
   241  	// StepDelay specifies the interval between peeks.
   242  	StepDelay Duration `json:"stepDelay"`
   243  }
   244  
   245  // TimeLimitedLoad spreads the operation starts out evenly over a given amount of time.
   246  type TimeLimitedLoad struct {
   247  	// TimeLimit specifies the amount of time that the operations will be spread over.
   248  	TimeLimit Duration `json:"timeLimit"`
   249  }
   250  
   251  // RandomizedTimeLimitedLoad makes an independent choice for each operation, choosing when
   252  // it starts uniformly at random from the given total duration.
   253  type RandomizedTimeLimitedLoad struct {
   254  	// TimeLimit specifies the amount of time that the operations will be spread over.
   255  	TimeLimit Duration `json:"timeLimit"`
   256  }
   257  
   258  // ParallelismLimitedLoad does the operations as quickly as possible subject to a given
   259  // limit on the number running concurrently.
   260  type ParallelismLimitedLoad struct {
   261  	// ParallelismLimit specifies the limit of the parallelism for the action executions.
   262  	ParallelismLimit int32 `json:"parallelismLimit"`
   263  }
   264  
   265  // GlobalQPSLoad defines a uniform load with a given QPS and Burst.
   266  // The rate limiter is shared across all phases using this tuning set.
   267  type GlobalQPSLoad struct {
   268  	// QPS defines desired average rate of actions.
   269  	QPS float64 `json:"qps"`
   270  	// Burst defines maxumim number of actions that can happen at the same time.
   271  	Burst int `json:"burst"`
   272  }
   273  
   274  // ChaosMonkeyConfig descibes simulated component failures.
   275  type ChaosMonkeyConfig struct {
   276  	// NodeFailure is a config for simulated node failures.
   277  	NodeFailure *NodeFailureConfig `json:"nodeFailure"`
   278  	// ExcludedNodes is a config for excluding certain nodes from failure.
   279  	ExcludedNodes sets.String `json:"excludedNodes"`
   280  }
   281  
   282  // NodeFailureConfig describes simulated node failures.
   283  type NodeFailureConfig struct {
   284  	// FailureRate is a percentage of all nodes that could fail simultinously.
   285  	FailureRate float64 `json:"failureRate"`
   286  	// Interval is time between node failures.
   287  	Interval Duration `json:"interval"`
   288  	// JitterFactor is factor used to jitter node failures.
   289  	// Node will be killed between [Interval, Interval + (1.0 + JitterFactor)].
   290  	JitterFactor float64 `json:"jitterFactor"`
   291  	// SimulatedDowntime is a duration between node is killed and recreated.
   292  	SimulatedDowntime Duration `json:"simulatedDowntime"`
   293  }
   294  
   295  // Duration is time.Duration that uses string format (e.g. 1h2m3s) for marshaling.
   296  type Duration time.Duration