UNPKG

@soft-stech/keda

Version:
758 lines 467 kB
import { z } from "zod"; import { iObjectMetaSchema } from "@soft-stech/apimachinery/apis/meta/v1/ObjectMeta.schema"; /** * ScaledJob is the Schema for the scaledjobs API */ export const IScaledJobSchema = z.object({ /** * APIVersion defines the versioned schema of this representation of an object. * Servers should convert recognized schemas to the latest internal value, and * may reject unrecognized values. * More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources */ apiVersion: z.literal("keda.sh/v1alpha1"), /** * Kind is a string value representing the REST resource this object represents. * Servers may infer this from the endpoint the client submits requests to. * Cannot be updated. * In CamelCase. * More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds */ kind: z.literal("ScaledJob"), metadata: iObjectMetaSchema.optional(), /** * ScaledJobSpec defines the desired state of ScaledJob */ spec: z .object({ envSourceContainerName: z.string().optional(), /** * * @format int32 */ failedJobsHistoryLimit: z.int32().optional(), /** * JobSpec describes how the job execution will look like. */ jobTargetRef: z.object({ /** * Specifies the duration in seconds relative to the startTime that the job * may be continuously active before the system tries to terminate it; value * must be positive integer. If a Job is suspended (at creation or through an * update), this timer will effectively be stopped and reset when the Job is * resumed again. */ activeDeadlineSeconds: z.number().optional(), /** * Specifies the number of retries before marking this job failed. * Defaults to 6 * @format int32 */ backoffLimit: z.int32().optional(), /** * Specifies the limit for the number of retries within an * index before marking this index as failed. When enabled the number of * failures per index is kept in the pod's * batch.kubernetes.io/job-index-failure-count annotation. It can only * be set when Job's completionMode=Indexed, and the Pod's restart * policy is Never. The field is immutable. * This field is beta-level. It can be used when the `JobBackoffLimitPerIndex` * feature gate is enabled (enabled by default). * @format int32 */ backoffLimitPerIndex: z.int32().optional(), /** * completionMode specifies how Pod completions are tracked. It can be * `NonIndexed` (default) or `Indexed`. * * * `NonIndexed` means that the Job is considered complete when there have * been .spec.completions successfully completed Pods. Each Pod completion is * homologous to each other. * * * `Indexed` means that the Pods of a * Job get an associated completion index from 0 to (.spec.completions - 1), * available in the annotation batch.kubernetes.io/job-completion-index. * The Job is considered complete when there is one successfully completed Pod * for each index. * When value is `Indexed`, .spec.completions must be specified and * `.spec.parallelism` must be less than or equal to 10^5. * In addition, The Pod name takes the form * `$(job-name)-$(index)-$(random-string)`, * the Pod hostname takes the form `$(job-name)-$(index)`. * * * More completion modes can be added in the future. * If the Job controller observes a mode that it doesn't recognize, which * is possible during upgrades due to version skew, the controller * skips updates for the Job. */ completionMode: z.string().optional(), /** * Specifies the desired number of successfully finished pods the * job should be run with. Setting to null means that the success of any * pod signals the success of all pods, and allows parallelism to have any positive * value. Setting to 1 means that parallelism is limited to 1 and the success of that * pod signals the success of the job. * More info: https://kubernetes.io/docs/concepts/workloads/controllers/jobs-run-to-completion/ * @format int32 */ completions: z.int32().optional(), /** * manualSelector controls generation of pod labels and pod selectors. * Leave `manualSelector` unset unless you are certain what you are doing. * When false or unset, the system pick labels unique to this job * and appends those labels to the pod template. When true, * the user is responsible for picking unique labels and specifying * the selector. Failure to pick a unique label may cause this * and other jobs to not function correctly. However, You may see * `manualSelector=true` in jobs that were created with the old `extensions/v1beta1` * API. * More info: https://kubernetes.io/docs/concepts/workloads/controllers/jobs-run-to-completion/#specifying-your-own-pod-selector */ manualSelector: z.boolean().optional(), /** * Specifies the maximal number of failed indexes before marking the Job as * failed, when backoffLimitPerIndex is set. Once the number of failed * indexes exceeds this number the entire Job is marked as Failed and its * execution is terminated. When left as null the job continues execution of * all of its indexes and is marked with the `Complete` Job condition. * It can only be specified when backoffLimitPerIndex is set. * It can be null or up to completions. It is required and must be * less than or equal to 10^4 when is completions greater than 10^5. * This field is beta-level. It can be used when the `JobBackoffLimitPerIndex` * feature gate is enabled (enabled by default). * @format int32 */ maxFailedIndexes: z.int32().optional(), /** * Specifies the maximum desired number of pods the job should * run at any given time. The actual number of pods running in steady state will * be less than this number when ((.spec.completions - .status.successful) < .spec.parallelism), * i.e. when the work left to do is less than max parallelism. * More info: https://kubernetes.io/docs/concepts/workloads/controllers/jobs-run-to-completion/ * @format int32 */ parallelism: z.int32().optional(), /** * Specifies the policy of handling failed pods. In particular, it allows to * specify the set of actions and conditions which need to be * satisfied to take the associated action. * If empty, the default behaviour applies - the counter of failed pods, * represented by the jobs's .status.failed field, is incremented and it is * checked against the backoffLimit. This field cannot be used in combination * with restartPolicy=OnFailure. * * * This field is beta-level. It can be used when the `JobPodFailurePolicy` * feature gate is enabled (enabled by default). */ podFailurePolicy: z .object({ /** * A list of pod failure policy rules. The rules are evaluated in order. * Once a rule matches a Pod failure, the remaining of the rules are ignored. * When no rule matches the Pod failure, the default handling applies - the * counter of pod failures is incremented and it is checked against * the backoffLimit. At most 20 elements are allowed. */ rules: z.array(z.object({ /** * Specifies the action taken on a pod failure when the requirements are satisfied. * Possible values are: * * * - FailJob: indicates that the pod's job is marked as Failed and all * running pods are terminated. * - FailIndex: indicates that the pod's index is marked as Failed and will * not be restarted. * This value is beta-level. It can be used when the * `JobBackoffLimitPerIndex` feature gate is enabled (enabled by default). * - Ignore: indicates that the counter towards the .backoffLimit is not * incremented and a replacement pod is created. * - Count: indicates that the pod is handled in the default way - the * counter towards the .backoffLimit is incremented. * Additional values are considered to be added in the future. Clients should * react to an unknown action by skipping the rule. */ action: z.string(), /** * Represents the requirement on the container exit codes. */ onExitCodes: z .object({ /** * Restricts the check for exit codes to the container with the * specified name. When null, the rule applies to all containers. * When specified, it should match one the container or initContainer * names in the pod template. */ containerName: z.string().optional(), /** * Represents the relationship between the container exit code(s) and the * specified values. Containers completed with success (exit code 0) are * excluded from the requirement check. Possible values are: * * * - In: the requirement is satisfied if at least one container exit code * (might be multiple if there are multiple containers not restricted * by the 'containerName' field) is in the set of specified values. * - NotIn: the requirement is satisfied if at least one container exit code * (might be multiple if there are multiple containers not restricted * by the 'containerName' field) is not in the set of specified values. * Additional values are considered to be added in the future. Clients should * react to an unknown operator by assuming the requirement is not satisfied. */ operator: z.string(), /** * Specifies the set of values. Each returned container exit code (might be * multiple in case of multiple containers) is checked against this set of * values with respect to the operator. The list of values must be ordered * and must not contain duplicates. Value '0' cannot be used for the In operator. * At least one element is required. At most 255 elements are allowed. */ values: z.array(z.number()) }) .optional(), /** * Represents the requirement on the pod conditions. The requirement is represented * as a list of pod condition patterns. The requirement is satisfied if at * least one pattern matches an actual pod condition. At most 20 elements are allowed. */ onPodConditions: z .array(z.object({ /** * Specifies the required Pod condition status. To match a pod condition * it is required that the specified status equals the pod condition status. * Defaults to True. */ status: z.string(), /** * Specifies the required Pod condition type. To match a pod condition * it is required that specified type equals the pod condition type. */ type: z.string() })) .optional() })) }) .optional(), /** * podReplacementPolicy specifies when to create replacement Pods. * Possible values are: * - TerminatingOrFailed means that we recreate pods * when they are terminating (has a metadata.deletionTimestamp) or failed. * - Failed means to wait until a previously created Pod is fully terminated (has phase * Failed or Succeeded) before creating a replacement Pod. * * * When using podFailurePolicy, Failed is the the only allowed value. * TerminatingOrFailed and Failed are allowed values when podFailurePolicy is not in use. * This is an beta field. To use this, enable the JobPodReplacementPolicy feature toggle. * This is on by default. */ podReplacementPolicy: z.string().optional(), /** * A label query over pods that should match the pod count. * Normally, the system sets this field for you. * More info: https://kubernetes.io/docs/concepts/overview/working-with-objects/labels/#label-selectors */ selector: z .object({ /** * matchExpressions is a list of label selector requirements. The requirements are ANDed. */ matchExpressions: z .array(z.object({ /** * key is the label key that the selector applies to. */ key: z.string(), /** * operator represents a key's relationship to a set of values. * Valid operators are In, NotIn, Exists and DoesNotExist. */ operator: z.string(), /** * values is an array of string values. If the operator is In or NotIn, * the values array must be non-empty. If the operator is Exists or DoesNotExist, * the values array must be empty. This array is replaced during a strategic * merge patch. */ values: z.array(z.string()).optional() })) .optional(), /** * matchLabels is a map of {key,value} pairs. A single {key,value} in the matchLabels * map is equivalent to an element of matchExpressions, whose key field is "key", the * operator is "In", and the values array contains only "value". The requirements are ANDed. */ matchLabels: z.record(z.string(), z.string()).optional() }) .optional(), /** * suspend specifies whether the Job controller should create Pods or not. If * a Job is created with suspend set to true, no Pods are created by the Job * controller. If a Job is suspended after creation (i.e. the flag goes from * false to true), the Job controller will delete all active Pods associated * with this Job. Users must design their workload to gracefully handle this. * Suspending a Job will reset the StartTime field of the Job, effectively * resetting the ActiveDeadlineSeconds timer too. Defaults to false. */ suspend: z.boolean().optional(), /** * Describes the pod that will be created when executing a job. * The only allowed template.spec.restartPolicy values are "Never" or "OnFailure". * More info: https://kubernetes.io/docs/concepts/workloads/controllers/jobs-run-to-completion/ */ template: z.object({ /** * Standard object's metadata. * More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata */ metadata: z.object({}).optional(), /** * Specification of the desired behavior of the pod. * More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#spec-and-status */ spec: z .object({ /** * Optional duration in seconds the pod may be active on the node relative to * StartTime before the system will actively try to mark it failed and kill associated containers. * Value must be a positive integer. */ activeDeadlineSeconds: z.number().optional(), /** * If specified, the pod's scheduling constraints */ affinity: z .object({ /** * Describes node affinity scheduling rules for the pod. */ nodeAffinity: z .object({ /** * The scheduler will prefer to schedule pods to nodes that satisfy * the affinity expressions specified by this field, but it may choose * a node that violates one or more of the expressions. The node that is * most preferred is the one with the greatest sum of weights, i.e. * for each node that meets all of the scheduling requirements (resource * request, requiredDuringScheduling affinity expressions, etc.), * compute a sum by iterating through the elements of this field and adding * "weight" to the sum if the node matches the corresponding matchExpressions; the * node(s) with the highest sum are the most preferred. */ preferredDuringSchedulingIgnoredDuringExecution: z .array(z.object({ /** * A node selector term, associated with the corresponding weight. */ preference: z.object({ /** * A list of node selector requirements by node's labels. */ matchExpressions: z .array(z.object({ /** * The label key that the selector applies to. */ key: z.string(), /** * Represents a key's relationship to a set of values. * Valid operators are In, NotIn, Exists, DoesNotExist. Gt, and Lt. */ operator: z.string(), /** * An array of string values. If the operator is In or NotIn, * the values array must be non-empty. If the operator is Exists or DoesNotExist, * the values array must be empty. If the operator is Gt or Lt, the values * array must have a single element, which will be interpreted as an integer. * This array is replaced during a strategic merge patch. */ values: z.array(z.string()).optional() })) .optional(), /** * A list of node selector requirements by node's fields. */ matchFields: z .array(z.object({ /** * The label key that the selector applies to. */ key: z.string(), /** * Represents a key's relationship to a set of values. * Valid operators are In, NotIn, Exists, DoesNotExist. Gt, and Lt. */ operator: z.string(), /** * An array of string values. If the operator is In or NotIn, * the values array must be non-empty. If the operator is Exists or DoesNotExist, * the values array must be empty. If the operator is Gt or Lt, the values * array must have a single element, which will be interpreted as an integer. * This array is replaced during a strategic merge patch. */ values: z.array(z.string()).optional() })) .optional() }), /** * Weight associated with matching the corresponding nodeSelectorTerm, in the range 1-100. * @format int32 */ weight: z.int32() })) .optional(), /** * If the affinity requirements specified by this field are not met at * scheduling time, the pod will not be scheduled onto the node. * If the affinity requirements specified by this field cease to be met * at some point during pod execution (e.g. due to an update), the system * may or may not try to eventually evict the pod from its node. */ requiredDuringSchedulingIgnoredDuringExecution: z .object({ /** * Required. A list of node selector terms. The terms are ORed. */ nodeSelectorTerms: z.array(z.object({ /** * A list of node selector requirements by node's labels. */ matchExpressions: z .array(z.object({ /** * The label key that the selector applies to. */ key: z.string(), /** * Represents a key's relationship to a set of values. * Valid operators are In, NotIn, Exists, DoesNotExist. Gt, and Lt. */ operator: z.string(), /** * An array of string values. If the operator is In or NotIn, * the values array must be non-empty. If the operator is Exists or DoesNotExist, * the values array must be empty. If the operator is Gt or Lt, the values * array must have a single element, which will be interpreted as an integer. * This array is replaced during a strategic merge patch. */ values: z.array(z.string()).optional() })) .optional(), /** * A list of node selector requirements by node's fields. */ matchFields: z .array(z.object({ /** * The label key that the selector applies to. */ key: z.string(), /** * Represents a key's relationship to a set of values. * Valid operators are In, NotIn, Exists, DoesNotExist. Gt, and Lt. */ operator: z.string(), /** * An array of string values. If the operator is In or NotIn, * the values array must be non-empty. If the operator is Exists or DoesNotExist, * the values array must be empty. If the operator is Gt or Lt, the values * array must have a single element, which will be interpreted as an integer. * This array is replaced during a strategic merge patch. */ values: z.array(z.string()).optional() })) .optional() })) }) .optional() }) .optional(), /** * Describes pod affinity scheduling rules (e.g. co-locate this pod in the same node, zone, etc. as some other pod(s)). */ podAffinity: z .object({ /** * The scheduler will prefer to schedule pods to nodes that satisfy * the affinity expressions specified by this field, but it may choose * a node that violates one or more of the expressions. The node that is * most preferred is the one with the greatest sum of weights, i.e. * for each node that meets all of the scheduling requirements (resource * request, requiredDuringScheduling affinity expressions, etc.), * compute a sum by iterating through the elements of this field and adding * "weight" to the sum if the node has pods which matches the corresponding podAffinityTerm; the * node(s) with the highest sum are the most preferred. */ preferredDuringSchedulingIgnoredDuringExecution: z .array(z.object({ /** * Required. A pod affinity term, associated with the corresponding weight. */ podAffinityTerm: z.object({ /** * A label query over a set of resources, in this case pods. * If it's null, this PodAffinityTerm matches with no Pods. */ labelSelector: z .object({ /** * matchExpressions is a list of label selector requirements. The requirements are ANDed. */ matchExpressions: z .array(z.object({ /** * key is the label key that the selector applies to. */ key: z.string(), /** * operator represents a key's relationship to a set of values. * Valid operators are In, NotIn, Exists and DoesNotExist. */ operator: z.string(), /** * values is an array of string values. If the operator is In or NotIn, * the values array must be non-empty. If the operator is Exists or DoesNotExist, * the values array must be empty. This array is replaced during a strategic * merge patch. */ values: z.array(z.string()).optional() })) .optional(), /** * matchLabels is a map of {key,value} pairs. A single {key,value} in the matchLabels * map is equivalent to an element of matchExpressions, whose key field is "key", the * operator is "In", and the values array contains only "value". The requirements are ANDed. */ matchLabels: z .record(z.string(), z.string()) .optional() }) .optional(), /** * MatchLabelKeys is a set of pod label keys to select which pods will * be taken into consideration. The keys are used to lookup values from the * incoming pod labels, those key-value labels are merged with `LabelSelector` as `key in (value)` * to select the group of existing pods which pods will be taken into consideration * for the incoming pod's pod (anti) affinity. Keys that don't exist in the incoming * pod labels will be ignored. The default value is empty. * The same key is forbidden to exist in both MatchLabelKeys and LabelSelector. * Also, MatchLabelKeys cannot be set when LabelSelector isn't set. * This is an alpha field and requires enabling MatchLabelKeysInPodAffinity feature gate. */ matchLabelKeys: z.array(z.string()).optional(), /** * MismatchLabelKeys is a set of pod label keys to select which pods will * be taken into consideration. The keys are used to lookup values from the * incoming pod labels, those key-value labels are merged with `LabelSelector` as `key notin (value)` * to select the group of existing pods which pods will be taken into consideration * for the incoming pod's pod (anti) affinity. Keys that don't exist in the incoming * pod labels will be ignored. The default value is empty. * The same key is forbidden to exist in both MismatchLabelKeys and LabelSelector. * Also, MismatchLabelKeys cannot be set when LabelSelector isn't set. * This is an alpha field and requires enabling MatchLabelKeysInPodAffinity feature gate. */ mismatchLabelKeys: z.array(z.string()).optional(), /** * A label query over the set of namespaces that the term applies to. * The term is applied to the union of the namespaces selected by this field * and the ones listed in the namespaces field. * null selector and null or empty namespaces list means "this pod's namespace". * An empty selector ({}) matches all namespaces. */ namespaceSelector: z .object({ /** * matchExpressions is a list of label selector requirements. The requirements are ANDed. */ matchExpressions: z .array(z.object({ /** * key is the label key that the selector applies to. */ key: z.string(), /** * operator represents a key's relationship to a set of values. * Valid operators are In, NotIn, Exists and DoesNotExist. */ operator: z.string(), /** * values is an array of string values. If the operator is In or NotIn, * the values array must be non-empty. If the operator is Exists or DoesNotExist, * the values array must be empty. This array is replaced during a strategic * merge patch. */ values: z.array(z.string()).optional() })) .optional(), /** * matchLabels is a map of {key,value} pairs. A single {key,value} in the matchLabels * map is equivalent to an element of matchExpressions, whose key field is "key", the * operator is "In", and the values array contains only "value". The requirements are ANDed. */ matchLabels: z .record(z.string(), z.string()) .optional() }) .optional(), /** * namespaces specifies a static list of namespace names that the term applies to. * The term is applied to the union of the namespaces listed in this field * and the ones selected by namespaceSelector. * null or empty namespaces list and null namespaceSelector means "this pod's namespace". */ namespaces: z.array(z.string()).optional(), /** * This pod should be co-located (affinity) or not co-located (anti-affinity) with the pods matching * the labelSelector in the specified namespaces, where co-located is defined as running on a node * whose value of the label with key topologyKey matches that of any node on which any of the * selected pods is running. * Empty topologyKey is not allowed. */ topologyKey: z.string() }), /** * weight associated with matching the corresponding podAffinityTerm, * in the range 1-100. * @format int32 */ weight: z.int32() })) .optional(), /** * If the affinity requirements specified by this field are not met at * scheduling time, the pod will not be scheduled onto the node. * If the affinity requirements specified by this field cease to be met * at some point during pod execution (e.g. due to a pod label update), the * system may or may not try to eventually evict the pod from its node. * When there are multiple elements, the lists of nodes corresponding to each * podAffinityTerm are intersected, i.e. all terms must be satisfied. */ requiredDuringSchedulingIgnoredDuringExecution: z .array(z.object({ /** * A label query over a set of resources, in this case pods. * If it's null, this PodAffinityTerm matches with no Pods. */ labelSelector: z .object({ /** * matchExpressions is a list of label selector requirements. The requirements are ANDed. */ matchExpressions: z .array(z.object({ /** * key is the label key that the selector applies to. */ key: z.string(), /** * operator represents a key's relationship to a set of values. * Valid operators are In, NotIn, Exists and DoesNotExist. */ operator: z.string(), /** * values is an array of string values. If the operator is In or NotIn, * the values array must be non-empty. If the operator is Exists or DoesNotExist, * the values array must be empty. This array is replaced during a strategic * merge patch. */ values: z.array(z.string()).optional() })) .optional(), /** * matchLabels is a map of {key,value} pairs. A single {key,value} in the matchLabels * map is equivalent to an element of matchExpressions, whose key field is "key", the * operator is "In", and the values array contains only "value". The requirements are ANDed. */ matchLabels: z .record(z.string(), z.string()) .optional() }) .optional(), /** * MatchLabelKeys is a set of pod label keys to select which pods will * be taken into consideration. The keys are used to lookup values from the * incoming pod labels, those key-value labels are merged with `LabelSelector` as `key in (value)` * to select the group of existing pods which pods will be taken into consideration * for the incoming pod's pod (anti) affinity. Keys that don't exist in the incoming * pod labels will be ignored. The default value is empty. * The same key is forbidden to exist in both MatchLabelKeys and LabelSelector. * Also, MatchLabelKeys cannot be set when LabelSelector isn't set. * This is an alpha field and requires enabling MatchLabelKeysInPodAffinity feature gate. */ matchLabelKeys: z.array(z.string()).optional(), /** * MismatchLabelKeys is a set of pod label keys to select which pods will * be taken into consideration. The keys are used to lookup values from the * incoming pod labels, those key-value labels are merged with `LabelSelector` as `key notin (value)` * to select the group of existing pods which pods will be taken into consideration * for the incoming pod's pod (anti) affinity. Keys that don't exist in the incoming * pod labels will be ignored. The default value is empty. * The same key is forbidden to exist in both MismatchLabelKeys and LabelSelector. * Also, MismatchLabelKeys cannot be set when LabelSelector isn't set. * This is an alpha field and requires enabling MatchLabelKeysInPodAffinity feature gate. */ mismatchLabelKeys: z.array(z.string()).optional(), /** * A label query over the set of namespaces that the term applies to. * The term is applied to the union of the namespaces selected by this field * and the ones listed in the namespaces field. * null selector and null or empty namespaces list means "this pod's namespace". * An empty selector ({}) matches all namespaces. */ namespaceSelector: z .object({ /** * matchExpressions is a list of label selector requirements. The requirements are ANDed. */ matchExpressions: z .array(z.object({ /** * key is the label key that the selector applies to. */ key: z.string(), /** * operator represents a key's relationship to a set of values. * Valid operators are In, NotIn, Exists and DoesNotExist. */ operator: z.string(), /** * values is an array of string values. If the operator is In or NotIn, * the values array must be non-empty. If the operator is Exists or DoesNotExist, * the values array must be empty. This array is replaced during a strategic * merge patch. */ values: z.array(z.string()).optional() })) .optional(), /** * matchLabels is a map of {key,value} pairs. A single {key,value} in the matchLabels * map is equivalent to an element of matchExpressions, whose key field is "key", the * operator is "In", and the values array contains only "value". The requirements are ANDed. */ matchLabels: z .record(z.string(), z.string()) .optional() }) .optional(), /** * namespaces specifies a static list of namespace names that the term applies to. * The term is applied to the union of the namespaces listed in this field * and the ones selected by namespaceSelector. * null or empty namespaces list and null namespaceSelector means "this pod's namespace". */ namespaces: z.array(z.string()).optional(), /** * This pod should be co-located (affinity) or not co-located (anti-affinity) with the pods matching * the labelSelector in the specified namespaces, where co-located is defined as running on a node * whose value of the label with key topologyKey matches that of any node on which any of the * selected pods is running. * Empty topologyKey is not allowed. */ topologyKey: z.string() }