From 440946fb69f6b0708ac9f52278955be83a5d7f75 Mon Sep 17 00:00:00 2001 From: Sebastian Bernauer Date: Mon, 26 Sep 2022 14:50:58 +0200 Subject: [PATCH 01/19] Bump operator-rs to 0.25.0 --- Cargo.lock | 58 +- deploy/crd/kafkacluster.crd.yaml | 854 +++++++++++------- deploy/helm/kafka-operator/crds/crds.yaml | 324 ++++++- deploy/manifests/crds.yaml | 324 ++++++- rust/crd/Cargo.toml | 2 +- rust/operator-binary/Cargo.toml | 4 +- .../src/stackable-kafka-operator.rs | 5 +- rust/operator/Cargo.toml | 2 +- rust/operator/src/discovery.rs | 5 +- rust/operator/src/kafka_controller.rs | 35 +- 10 files changed, 1191 insertions(+), 422 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index d7771593..642882f4 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -840,9 +840,9 @@ dependencies = [ [[package]] name = "kube" -version = "0.73.1" +version = "0.74.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f68b954ea9ad888de953fb1488bd8f377c4c78d82d4642efa5925189210b50b7" +checksum = "a527a8001a61d8d470dab27ac650889938760c243903e7cd90faaf7c60a34bdd" dependencies = [ "k8s-openapi", "kube-client", @@ -853,9 +853,9 @@ dependencies = [ [[package]] name = "kube-client" -version = "0.73.1" +version = "0.74.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9150dc7107d9acf4986088f284a0a6dddc5ae37ef1ffdf142f6811dc5998dd58" +checksum = "c0d48f42df4e8342e9f488c4b97e3759d0042c4e7ab1a853cc285adb44409480" dependencies = [ "base64", "bytes", @@ -878,7 +878,7 @@ dependencies = [ "secrecy", "serde", "serde_json", - "serde_yaml", + "serde_yaml 0.8.26", "thiserror", "tokio", "tokio-native-tls", @@ -890,9 +890,9 @@ dependencies = [ [[package]] name = "kube-core" -version = "0.73.1" +version = "0.74.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bc8c429676abe6a73b374438d5ca02caaf9ae7a635441253c589b779fa5d0622" +checksum = "91f56027f862fdcad265d2e9616af416a355e28a1c620bb709083494753e070d" dependencies = [ "chrono", "form_urlencoded", @@ -908,9 +908,9 @@ dependencies = [ [[package]] name = "kube-derive" -version = "0.73.1" +version = "0.74.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bfb405f0d39181acbfdc7c79e3fc095330c9b6465ab50aeb662d762e53b662f1" +checksum = "66d74121eb41af4480052901f31142d8d9bbdf1b7c6b856da43bcb02f5b1b177" dependencies = [ "darling", "proc-macro2", @@ -921,9 +921,9 @@ dependencies = [ [[package]] name = "kube-runtime" -version = "0.73.1" +version = "0.74.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b6e9e9da456f0101b77f864a9da44866b9891ad4740db508b4b269343ebeb01d" +checksum = "8fdcf5a20f968768e342ef1a457491bb5661fccd81119666d626c57500b16d99" dependencies = [ "ahash", "backoff", @@ -1333,7 +1333,7 @@ dependencies = [ "semver", "serde", "serde_json", - "serde_yaml", + "serde_yaml 0.8.26", "thiserror", "xml-rs", ] @@ -1591,6 +1591,19 @@ dependencies = [ "yaml-rust", ] +[[package]] +name = "serde_yaml" +version = "0.9.13" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8613d593412a0deb7bbd8de9d908efff5a0cb9ccd8f62c641e7b2ed2f57291d1" +dependencies = [ + "indexmap", + "itoa", + "ryu", + "serde", + "unsafe-libyaml", +] + [[package]] name = "sharded-slab" version = "0.1.4" @@ -1663,7 +1676,7 @@ dependencies = [ "semver", "serde", "serde_json", - "serde_yaml", + "serde_yaml 0.8.26", "snafu", "stackable-operator", "strum", @@ -1690,7 +1703,7 @@ version = "0.8.0-nightly" dependencies = [ "built", "clap", - "serde_yaml", + "serde_yaml 0.8.26", "stackable-kafka-crd", "stackable-kafka-operator", "stackable-operator", @@ -1700,10 +1713,9 @@ dependencies = [ [[package]] name = "stackable-operator" -version = "0.22.0" -source = "git+https://github.com/stackabletech/operator-rs.git?tag=0.22.0#5543877169d27770578e634d0d734aa6126f838c" +version = "0.25.0" +source = "git+https://github.com/stackabletech/operator-rs.git?tag=0.25.0#490ef77e05d86a0bc2b555fd5950593d9f3a5d4b" dependencies = [ - "backoff", "chrono", "clap", "const_format", @@ -1722,7 +1734,7 @@ dependencies = [ "schemars", "serde", "serde_json", - "serde_yaml", + "serde_yaml 0.9.13", "stackable-operator-derive", "strum", "thiserror", @@ -1734,8 +1746,8 @@ dependencies = [ [[package]] name = "stackable-operator-derive" -version = "0.22.0" -source = "git+https://github.com/stackabletech/operator-rs.git?tag=0.22.0#5543877169d27770578e634d0d734aa6126f838c" +version = "0.25.0" +source = "git+https://github.com/stackabletech/operator-rs.git?tag=0.25.0#490ef77e05d86a0bc2b555fd5950593d9f3a5d4b" dependencies = [ "darling", "proc-macro2", @@ -2152,6 +2164,12 @@ version = "0.2.4" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f962df74c8c05a667b5ee8bcf162993134c104e96440b663c8daa176dc772d8c" +[[package]] +name = "unsafe-libyaml" +version = "0.2.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c1e5fa573d8ac5f1a856f8d7be41d390ee973daf97c806b2c1a465e4e1406e68" + [[package]] name = "url" version = "2.3.1" diff --git a/deploy/crd/kafkacluster.crd.yaml b/deploy/crd/kafkacluster.crd.yaml index 5e709021..4f4fa65b 100644 --- a/deploy/crd/kafkacluster.crd.yaml +++ b/deploy/crd/kafkacluster.crd.yaml @@ -10,339 +10,587 @@ spec: kind: KafkaCluster plural: kafkaclusters shortNames: - - kafka + - kafka singular: kafkacluster scope: Namespaced versions: - - additionalPrinterColumns: [] - name: v1alpha1 - schema: - openAPIV3Schema: - description: "Auto-generated derived type for KafkaClusterSpec via `CustomResource`" - properties: - spec: - properties: - brokers: - nullable: true - properties: - cliOverrides: + - additionalPrinterColumns: [] + name: v1alpha1 + schema: + openAPIV3Schema: + description: Auto-generated derived type for KafkaClusterSpec via `CustomResource` + properties: + spec: + properties: + brokers: + nullable: true + properties: + cliOverrides: + additionalProperties: + type: string + default: {} + type: object + config: + default: {} + properties: + resources: + default: + memory: + limit: null + runtimeLimits: {} + cpu: + min: null + max: null + storage: + logDirs: + capacity: null + properties: + cpu: + default: + min: null + max: null + properties: + max: + description: |- + Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors. + + The serialization format is: + + ::= + (Note that may be empty, from the "" case in .) + ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= "+" | "-" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei + (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html) + ::= m | "" | k | M | G | T | P | E + (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.) + ::= "e" | "E" + + No matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities. + + When a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized. + + Before serializing, Quantity will be put in "canonical form". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that: + a. No precision is lost + b. No fractional digits will be emitted + c. The exponent (or suffix) is as large as possible. + The sign will be omitted unless the number is negative. + + Examples: + 1.5 will be serialized as "1500m" + 1.5Gi will be serialized as "1536Mi" + + Note that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise. + + Non-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.) + + This format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation. + nullable: true + type: string + min: + description: |- + Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors. + + The serialization format is: + + ::= + (Note that may be empty, from the "" case in .) + ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= "+" | "-" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei + (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html) + ::= m | "" | k | M | G | T | P | E + (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.) + ::= "e" | "E" + + No matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities. + + When a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized. + + Before serializing, Quantity will be put in "canonical form". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that: + a. No precision is lost + b. No fractional digits will be emitted + c. The exponent (or suffix) is as large as possible. + The sign will be omitted unless the number is negative. + + Examples: + 1.5 will be serialized as "1500m" + 1.5Gi will be serialized as "1536Mi" + + Note that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise. + + Non-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.) + + This format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation. + nullable: true + type: string + type: object + memory: + properties: + limit: + description: |- + Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors. + + The serialization format is: + + ::= + (Note that may be empty, from the "" case in .) + ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= "+" | "-" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei + (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html) + ::= m | "" | k | M | G | T | P | E + (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.) + ::= "e" | "E" + + No matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities. + + When a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized. + + Before serializing, Quantity will be put in "canonical form". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that: + a. No precision is lost + b. No fractional digits will be emitted + c. The exponent (or suffix) is as large as possible. + The sign will be omitted unless the number is negative. + + Examples: + 1.5 will be serialized as "1500m" + 1.5Gi will be serialized as "1536Mi" + + Note that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise. + + Non-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.) + + This format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation. + nullable: true + type: string + runtimeLimits: + type: object + type: object + storage: + properties: + logDirs: + default: + capacity: null + properties: + capacity: + description: |- + Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors. + + The serialization format is: + + ::= + (Note that may be empty, from the "" case in .) + ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= "+" | "-" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei + (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html) + ::= m | "" | k | M | G | T | P | E + (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.) + ::= "e" | "E" + + No matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities. + + When a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized. + + Before serializing, Quantity will be put in "canonical form". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that: + a. No precision is lost + b. No fractional digits will be emitted + c. The exponent (or suffix) is as large as possible. + The sign will be omitted unless the number is negative. + + Examples: + 1.5 will be serialized as "1500m" + 1.5Gi will be serialized as "1536Mi" + + Note that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise. + + Non-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.) + + This format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation. + nullable: true + type: string + selectors: + description: A label selector is a label query over a set of resources. The result of matchLabels and matchExpressions are ANDed. An empty label selector matches all objects. A null label selector matches no objects. + nullable: true + properties: + matchExpressions: + description: matchExpressions is a list of label selector requirements. The requirements are ANDed. + items: + description: A label selector requirement is a selector that contains values, a key, and an operator that relates the key and values. + properties: + key: + description: key is the label key that the selector applies to. + type: string + operator: + description: operator represents a key's relationship to a set of values. Valid operators are In, NotIn, Exists and DoesNotExist. + type: string + values: + description: 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. + items: + type: string + type: array + required: + - key + - operator + type: object + type: array + matchLabels: + additionalProperties: + type: string + description: 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. + type: object + type: object + storageClass: + nullable: true + type: string + type: object + type: object + type: object + type: object + configOverrides: + additionalProperties: additionalProperties: type: string - default: {} type: object - config: - default: {} + default: {} + type: object + envOverrides: + additionalProperties: + type: string + default: {} + type: object + roleGroups: + additionalProperties: properties: - resources: - default: - memory: - limit: ~ - runtimeLimits: {} - cpu: - min: ~ - max: ~ - storage: - logDirs: - capacity: ~ + cliOverrides: + additionalProperties: + type: string + default: {} + type: object + config: + default: {} properties: - cpu: + resources: default: - min: ~ - max: ~ + memory: + limit: null + runtimeLimits: {} + cpu: + min: null + max: null + storage: + logDirs: + capacity: null properties: - max: - description: "Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors.\n\nThe serialization format is:\n\n ::= \n (Note that may be empty, from the \"\" case in .)\n ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= \"+\" | \"-\" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei\n (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html)\n ::= m | \"\" | k | M | G | T | P | E\n (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.)\n ::= \"e\" | \"E\" \n\nNo matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities.\n\nWhen a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized.\n\nBefore serializing, Quantity will be put in \"canonical form\". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that:\n a. No precision is lost\n b. No fractional digits will be emitted\n c. The exponent (or suffix) is as large as possible.\nThe sign will be omitted unless the number is negative.\n\nExamples:\n 1.5 will be serialized as \"1500m\"\n 1.5Gi will be serialized as \"1536Mi\"\n\nNote that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise.\n\nNon-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.)\n\nThis format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation." - nullable: true - type: string - min: - description: "Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors.\n\nThe serialization format is:\n\n ::= \n (Note that may be empty, from the \"\" case in .)\n ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= \"+\" | \"-\" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei\n (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html)\n ::= m | \"\" | k | M | G | T | P | E\n (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.)\n ::= \"e\" | \"E\" \n\nNo matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities.\n\nWhen a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized.\n\nBefore serializing, Quantity will be put in \"canonical form\". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that:\n a. No precision is lost\n b. No fractional digits will be emitted\n c. The exponent (or suffix) is as large as possible.\nThe sign will be omitted unless the number is negative.\n\nExamples:\n 1.5 will be serialized as \"1500m\"\n 1.5Gi will be serialized as \"1536Mi\"\n\nNote that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise.\n\nNon-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.)\n\nThis format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation." - nullable: true - type: string - type: object - memory: - properties: - limit: - description: "Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors.\n\nThe serialization format is:\n\n ::= \n (Note that may be empty, from the \"\" case in .)\n ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= \"+\" | \"-\" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei\n (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html)\n ::= m | \"\" | k | M | G | T | P | E\n (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.)\n ::= \"e\" | \"E\" \n\nNo matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities.\n\nWhen a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized.\n\nBefore serializing, Quantity will be put in \"canonical form\". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that:\n a. No precision is lost\n b. No fractional digits will be emitted\n c. The exponent (or suffix) is as large as possible.\nThe sign will be omitted unless the number is negative.\n\nExamples:\n 1.5 will be serialized as \"1500m\"\n 1.5Gi will be serialized as \"1536Mi\"\n\nNote that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise.\n\nNon-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.)\n\nThis format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation." - nullable: true - type: string - runtimeLimits: - type: object - type: object - storage: - properties: - logDirs: + cpu: default: - capacity: ~ + min: null + max: null properties: - capacity: - description: "Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors.\n\nThe serialization format is:\n\n ::= \n (Note that may be empty, from the \"\" case in .)\n ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= \"+\" | \"-\" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei\n (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html)\n ::= m | \"\" | k | M | G | T | P | E\n (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.)\n ::= \"e\" | \"E\" \n\nNo matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities.\n\nWhen a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized.\n\nBefore serializing, Quantity will be put in \"canonical form\". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that:\n a. No precision is lost\n b. No fractional digits will be emitted\n c. The exponent (or suffix) is as large as possible.\nThe sign will be omitted unless the number is negative.\n\nExamples:\n 1.5 will be serialized as \"1500m\"\n 1.5Gi will be serialized as \"1536Mi\"\n\nNote that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise.\n\nNon-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.)\n\nThis format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation." + max: + description: |- + Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors. + + The serialization format is: + + ::= + (Note that may be empty, from the "" case in .) + ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= "+" | "-" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei + (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html) + ::= m | "" | k | M | G | T | P | E + (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.) + ::= "e" | "E" + + No matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities. + + When a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized. + + Before serializing, Quantity will be put in "canonical form". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that: + a. No precision is lost + b. No fractional digits will be emitted + c. The exponent (or suffix) is as large as possible. + The sign will be omitted unless the number is negative. + + Examples: + 1.5 will be serialized as "1500m" + 1.5Gi will be serialized as "1536Mi" + + Note that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise. + + Non-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.) + + This format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation. + nullable: true + type: string + min: + description: |- + Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors. + + The serialization format is: + + ::= + (Note that may be empty, from the "" case in .) + ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= "+" | "-" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei + (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html) + ::= m | "" | k | M | G | T | P | E + (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.) + ::= "e" | "E" + + No matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities. + + When a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized. + + Before serializing, Quantity will be put in "canonical form". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that: + a. No precision is lost + b. No fractional digits will be emitted + c. The exponent (or suffix) is as large as possible. + The sign will be omitted unless the number is negative. + + Examples: + 1.5 will be serialized as "1500m" + 1.5Gi will be serialized as "1536Mi" + + Note that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise. + + Non-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.) + + This format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation. nullable: true type: string - selectors: - description: A label selector is a label query over a set of resources. The result of matchLabels and matchExpressions are ANDed. An empty label selector matches all objects. A null label selector matches no objects. + type: object + memory: + properties: + limit: + description: |- + Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors. + + The serialization format is: + + ::= + (Note that may be empty, from the "" case in .) + ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= "+" | "-" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei + (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html) + ::= m | "" | k | M | G | T | P | E + (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.) + ::= "e" | "E" + + No matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities. + + When a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized. + + Before serializing, Quantity will be put in "canonical form". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that: + a. No precision is lost + b. No fractional digits will be emitted + c. The exponent (or suffix) is as large as possible. + The sign will be omitted unless the number is negative. + + Examples: + 1.5 will be serialized as "1500m" + 1.5Gi will be serialized as "1536Mi" + + Note that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise. + + Non-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.) + + This format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation. nullable: true + type: string + runtimeLimits: + type: object + type: object + storage: + properties: + logDirs: + default: + capacity: null properties: - matchExpressions: - description: matchExpressions is a list of label selector requirements. The requirements are ANDed. - items: - description: "A label selector requirement is a selector that contains values, a key, and an operator that relates the key and values." - properties: - key: - description: key is the label key that the selector applies to. - type: string - operator: - description: "operator represents a key's relationship to a set of values. Valid operators are In, NotIn, Exists and DoesNotExist." + capacity: + description: |- + Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors. + + The serialization format is: + + ::= + (Note that may be empty, from the "" case in .) + ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= "+" | "-" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei + (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html) + ::= m | "" | k | M | G | T | P | E + (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.) + ::= "e" | "E" + + No matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities. + + When a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized. + + Before serializing, Quantity will be put in "canonical form". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that: + a. No precision is lost + b. No fractional digits will be emitted + c. The exponent (or suffix) is as large as possible. + The sign will be omitted unless the number is negative. + + Examples: + 1.5 will be serialized as "1500m" + 1.5Gi will be serialized as "1536Mi" + + Note that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise. + + Non-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.) + + This format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation. + nullable: true + type: string + selectors: + description: A label selector is a label query over a set of resources. The result of matchLabels and matchExpressions are ANDed. An empty label selector matches all objects. A null label selector matches no objects. + nullable: true + properties: + matchExpressions: + description: matchExpressions is a list of label selector requirements. The requirements are ANDed. + items: + description: A label selector requirement is a selector that contains values, a key, and an operator that relates the key and values. + properties: + key: + description: key is the label key that the selector applies to. + type: string + operator: + description: operator represents a key's relationship to a set of values. Valid operators are In, NotIn, Exists and DoesNotExist. + type: string + values: + description: 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. + items: + type: string + type: array + required: + - key + - operator + type: object + type: array + matchLabels: + additionalProperties: type: string - values: - description: "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." - items: - type: string - type: array - required: - - key - - operator - type: object - type: array - matchLabels: - additionalProperties: - type: string - description: "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." + description: 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. + type: object type: object + storageClass: + nullable: true + type: string type: object - storageClass: - nullable: true - type: string type: object type: object type: object - type: object - configOverrides: - additionalProperties: - additionalProperties: - type: string - type: object - default: {} - type: object - envOverrides: - additionalProperties: - type: string - default: {} - type: object - roleGroups: - additionalProperties: - properties: - cliOverrides: + configOverrides: + additionalProperties: additionalProperties: type: string - default: {} type: object - config: - default: {} - properties: - resources: - default: - memory: - limit: ~ - runtimeLimits: {} - cpu: - min: ~ - max: ~ - storage: - logDirs: - capacity: ~ + default: {} + type: object + envOverrides: + additionalProperties: + type: string + default: {} + type: object + replicas: + format: uint16 + minimum: 0.0 + nullable: true + type: integer + selector: + description: A label selector is a label query over a set of resources. The result of matchLabels and matchExpressions are ANDed. An empty label selector matches all objects. A null label selector matches no objects. + nullable: true + properties: + matchExpressions: + description: matchExpressions is a list of label selector requirements. The requirements are ANDed. + items: + description: A label selector requirement is a selector that contains values, a key, and an operator that relates the key and values. properties: - cpu: - default: - min: ~ - max: ~ - properties: - max: - description: "Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors.\n\nThe serialization format is:\n\n ::= \n (Note that may be empty, from the \"\" case in .)\n ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= \"+\" | \"-\" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei\n (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html)\n ::= m | \"\" | k | M | G | T | P | E\n (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.)\n ::= \"e\" | \"E\" \n\nNo matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities.\n\nWhen a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized.\n\nBefore serializing, Quantity will be put in \"canonical form\". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that:\n a. No precision is lost\n b. No fractional digits will be emitted\n c. The exponent (or suffix) is as large as possible.\nThe sign will be omitted unless the number is negative.\n\nExamples:\n 1.5 will be serialized as \"1500m\"\n 1.5Gi will be serialized as \"1536Mi\"\n\nNote that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise.\n\nNon-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.)\n\nThis format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation." - nullable: true - type: string - min: - description: "Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors.\n\nThe serialization format is:\n\n ::= \n (Note that may be empty, from the \"\" case in .)\n ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= \"+\" | \"-\" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei\n (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html)\n ::= m | \"\" | k | M | G | T | P | E\n (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.)\n ::= \"e\" | \"E\" \n\nNo matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities.\n\nWhen a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized.\n\nBefore serializing, Quantity will be put in \"canonical form\". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that:\n a. No precision is lost\n b. No fractional digits will be emitted\n c. The exponent (or suffix) is as large as possible.\nThe sign will be omitted unless the number is negative.\n\nExamples:\n 1.5 will be serialized as \"1500m\"\n 1.5Gi will be serialized as \"1536Mi\"\n\nNote that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise.\n\nNon-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.)\n\nThis format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation." - nullable: true - type: string - type: object - memory: - properties: - limit: - description: "Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors.\n\nThe serialization format is:\n\n ::= \n (Note that may be empty, from the \"\" case in .)\n ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= \"+\" | \"-\" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei\n (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html)\n ::= m | \"\" | k | M | G | T | P | E\n (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.)\n ::= \"e\" | \"E\" \n\nNo matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities.\n\nWhen a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized.\n\nBefore serializing, Quantity will be put in \"canonical form\". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that:\n a. No precision is lost\n b. No fractional digits will be emitted\n c. The exponent (or suffix) is as large as possible.\nThe sign will be omitted unless the number is negative.\n\nExamples:\n 1.5 will be serialized as \"1500m\"\n 1.5Gi will be serialized as \"1536Mi\"\n\nNote that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise.\n\nNon-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.)\n\nThis format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation." - nullable: true - type: string - runtimeLimits: - type: object - type: object - storage: - properties: - logDirs: - default: - capacity: ~ - properties: - capacity: - description: "Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors.\n\nThe serialization format is:\n\n ::= \n (Note that may be empty, from the \"\" case in .)\n ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= \"+\" | \"-\" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei\n (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html)\n ::= m | \"\" | k | M | G | T | P | E\n (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.)\n ::= \"e\" | \"E\" \n\nNo matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities.\n\nWhen a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized.\n\nBefore serializing, Quantity will be put in \"canonical form\". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that:\n a. No precision is lost\n b. No fractional digits will be emitted\n c. The exponent (or suffix) is as large as possible.\nThe sign will be omitted unless the number is negative.\n\nExamples:\n 1.5 will be serialized as \"1500m\"\n 1.5Gi will be serialized as \"1536Mi\"\n\nNote that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise.\n\nNon-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.)\n\nThis format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation." - nullable: true - type: string - selectors: - description: A label selector is a label query over a set of resources. The result of matchLabels and matchExpressions are ANDed. An empty label selector matches all objects. A null label selector matches no objects. - nullable: true - properties: - matchExpressions: - description: matchExpressions is a list of label selector requirements. The requirements are ANDed. - items: - description: "A label selector requirement is a selector that contains values, a key, and an operator that relates the key and values." - properties: - key: - description: key is the label key that the selector applies to. - type: string - operator: - description: "operator represents a key's relationship to a set of values. Valid operators are In, NotIn, Exists and DoesNotExist." - type: string - values: - description: "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." - items: - type: string - type: array - required: - - key - - operator - type: object - type: array - matchLabels: - additionalProperties: - type: string - description: "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." - type: object - type: object - storageClass: - nullable: true - type: string - type: object - type: object + key: + description: key is the label key that the selector applies to. + type: string + operator: + description: operator represents a key's relationship to a set of values. Valid operators are In, NotIn, Exists and DoesNotExist. + type: string + values: + description: 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. + items: + type: string + type: array + required: + - key + - operator type: object - type: object - configOverrides: - additionalProperties: + type: array + matchLabels: additionalProperties: type: string + description: 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. type: object - default: {} - type: object - envOverrides: - additionalProperties: - type: string - default: {} - type: object - replicas: - format: uint16 - minimum: 0.0 - nullable: true - type: integer - selector: - description: A label selector is a label query over a set of resources. The result of matchLabels and matchExpressions are ANDed. An empty label selector matches all objects. A null label selector matches no objects. - nullable: true - properties: - matchExpressions: - description: matchExpressions is a list of label selector requirements. The requirements are ANDed. - items: - description: "A label selector requirement is a selector that contains values, a key, and an operator that relates the key and values." - properties: - key: - description: key is the label key that the selector applies to. - type: string - operator: - description: "operator represents a key's relationship to a set of values. Valid operators are In, NotIn, Exists and DoesNotExist." - type: string - values: - description: "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." - items: - type: string - type: array - required: - - key - - operator - type: object - type: array - matchLabels: - additionalProperties: - type: string - description: "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." - type: object - type: object - type: object + type: object type: object - required: - - roleGroups - type: object - config: - default: - tls: + type: object + required: + - roleGroups + type: object + config: + default: + tls: + secretClass: tls + internalTls: + secretClass: tls + properties: + clientAuthentication: + description: 'Only affects client connections. This setting controls: - If clients need to authenticate themselves against the server via TLS - Which ca.crt to use when validating the provided client certs Defaults to `None`' + nullable: true + properties: + authenticationClass: + type: string + required: + - authenticationClass + type: object + internalTls: + default: secretClass: tls - internalTls: + description: 'Only affects internal communication. Use mutual verification between Kafka nodes This setting controls: - Which cert the servers should use to authenticate themselves against other servers - Which ca.crt to use when validating the other server' + nullable: true + properties: + secretClass: + type: string + required: + - secretClass + type: object + tls: + default: secretClass: tls - properties: - clientAuthentication: - description: "Only affects client connections. This setting controls: - If clients need to authenticate themselves against the server via TLS - Which ca.crt to use when validating the provided client certs Defaults to `None`" - nullable: true - properties: - authenticationClass: - type: string - required: - - authenticationClass - type: object - internalTls: - default: - secretClass: tls - description: "Only affects internal communication. Use mutual verification between Kafka nodes This setting controls: - Which cert the servers should use to authenticate themselves against other servers - Which ca.crt to use when validating the other server" - nullable: true - properties: - secretClass: - type: string - required: - - secretClass - type: object - tls: - default: - secretClass: tls - description: "Only affects client connections. This setting controls: - If TLS encryption is used at all - Which cert the servers should use to authenticate themselves against the client Defaults to `TlsSecretClass` { secret_class: \"tls\".to_string() }." - nullable: true - properties: - secretClass: - type: string - required: - - secretClass - type: object - type: object - log4j: - nullable: true - type: string - opa: - nullable: true - properties: - configMapName: - type: string - package: - nullable: true - type: string - required: - - configMapName - type: object - stopped: - nullable: true - type: boolean - version: - nullable: true - type: string - zookeeperConfigMapName: - type: string - required: - - zookeeperConfigMapName - type: object - required: - - spec - title: KafkaCluster - type: object - served: true - storage: true - subresources: {} + description: 'Only affects client connections. This setting controls: - If TLS encryption is used at all - Which cert the servers should use to authenticate themselves against the client Defaults to `TlsSecretClass` { secret_class: "tls".to_string() }.' + nullable: true + properties: + secretClass: + type: string + required: + - secretClass + type: object + type: object + log4j: + nullable: true + type: string + opa: + nullable: true + properties: + configMapName: + type: string + package: + nullable: true + type: string + required: + - configMapName + type: object + stopped: + nullable: true + type: boolean + version: + nullable: true + type: string + zookeeperConfigMapName: + type: string + required: + - zookeeperConfigMapName + type: object + required: + - spec + title: KafkaCluster + type: object + served: true + storage: true + subresources: {} diff --git a/deploy/helm/kafka-operator/crds/crds.yaml b/deploy/helm/kafka-operator/crds/crds.yaml index e9e2858c..4fd32a5b 100644 --- a/deploy/helm/kafka-operator/crds/crds.yaml +++ b/deploy/helm/kafka-operator/crds/crds.yaml @@ -20,7 +20,7 @@ spec: name: v1alpha1 schema: openAPIV3Schema: - description: "Auto-generated derived type for KafkaClusterSpec via `CustomResource`" + description: Auto-generated derived type for KafkaClusterSpec via `CustomResource` properties: spec: properties: @@ -38,33 +38,126 @@ spec: resources: default: memory: - limit: ~ + limit: null runtimeLimits: {} cpu: - min: ~ - max: ~ + min: null + max: null storage: logDirs: - capacity: ~ + capacity: null properties: cpu: default: - min: ~ - max: ~ + min: null + max: null properties: max: - description: "Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors.\n\nThe serialization format is:\n\n ::= \n (Note that may be empty, from the \"\" case in .)\n ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= \"+\" | \"-\" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei\n (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html)\n ::= m | \"\" | k | M | G | T | P | E\n (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.)\n ::= \"e\" | \"E\" \n\nNo matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities.\n\nWhen a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized.\n\nBefore serializing, Quantity will be put in \"canonical form\". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that:\n a. No precision is lost\n b. No fractional digits will be emitted\n c. The exponent (or suffix) is as large as possible.\nThe sign will be omitted unless the number is negative.\n\nExamples:\n 1.5 will be serialized as \"1500m\"\n 1.5Gi will be serialized as \"1536Mi\"\n\nNote that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise.\n\nNon-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.)\n\nThis format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation." + description: |- + Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors. + + The serialization format is: + + ::= + (Note that may be empty, from the "" case in .) + ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= "+" | "-" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei + (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html) + ::= m | "" | k | M | G | T | P | E + (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.) + ::= "e" | "E" + + No matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities. + + When a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized. + + Before serializing, Quantity will be put in "canonical form". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that: + a. No precision is lost + b. No fractional digits will be emitted + c. The exponent (or suffix) is as large as possible. + The sign will be omitted unless the number is negative. + + Examples: + 1.5 will be serialized as "1500m" + 1.5Gi will be serialized as "1536Mi" + + Note that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise. + + Non-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.) + + This format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation. nullable: true type: string min: - description: "Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors.\n\nThe serialization format is:\n\n ::= \n (Note that may be empty, from the \"\" case in .)\n ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= \"+\" | \"-\" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei\n (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html)\n ::= m | \"\" | k | M | G | T | P | E\n (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.)\n ::= \"e\" | \"E\" \n\nNo matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities.\n\nWhen a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized.\n\nBefore serializing, Quantity will be put in \"canonical form\". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that:\n a. No precision is lost\n b. No fractional digits will be emitted\n c. The exponent (or suffix) is as large as possible.\nThe sign will be omitted unless the number is negative.\n\nExamples:\n 1.5 will be serialized as \"1500m\"\n 1.5Gi will be serialized as \"1536Mi\"\n\nNote that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise.\n\nNon-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.)\n\nThis format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation." + description: |- + Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors. + + The serialization format is: + + ::= + (Note that may be empty, from the "" case in .) + ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= "+" | "-" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei + (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html) + ::= m | "" | k | M | G | T | P | E + (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.) + ::= "e" | "E" + + No matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities. + + When a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized. + + Before serializing, Quantity will be put in "canonical form". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that: + a. No precision is lost + b. No fractional digits will be emitted + c. The exponent (or suffix) is as large as possible. + The sign will be omitted unless the number is negative. + + Examples: + 1.5 will be serialized as "1500m" + 1.5Gi will be serialized as "1536Mi" + + Note that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise. + + Non-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.) + + This format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation. nullable: true type: string type: object memory: properties: limit: - description: "Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors.\n\nThe serialization format is:\n\n ::= \n (Note that may be empty, from the \"\" case in .)\n ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= \"+\" | \"-\" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei\n (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html)\n ::= m | \"\" | k | M | G | T | P | E\n (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.)\n ::= \"e\" | \"E\" \n\nNo matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities.\n\nWhen a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized.\n\nBefore serializing, Quantity will be put in \"canonical form\". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that:\n a. No precision is lost\n b. No fractional digits will be emitted\n c. The exponent (or suffix) is as large as possible.\nThe sign will be omitted unless the number is negative.\n\nExamples:\n 1.5 will be serialized as \"1500m\"\n 1.5Gi will be serialized as \"1536Mi\"\n\nNote that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise.\n\nNon-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.)\n\nThis format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation." + description: |- + Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors. + + The serialization format is: + + ::= + (Note that may be empty, from the "" case in .) + ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= "+" | "-" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei + (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html) + ::= m | "" | k | M | G | T | P | E + (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.) + ::= "e" | "E" + + No matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities. + + When a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized. + + Before serializing, Quantity will be put in "canonical form". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that: + a. No precision is lost + b. No fractional digits will be emitted + c. The exponent (or suffix) is as large as possible. + The sign will be omitted unless the number is negative. + + Examples: + 1.5 will be serialized as "1500m" + 1.5Gi will be serialized as "1536Mi" + + Note that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise. + + Non-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.) + + This format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation. nullable: true type: string runtimeLimits: @@ -74,10 +167,41 @@ spec: properties: logDirs: default: - capacity: ~ + capacity: null properties: capacity: - description: "Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors.\n\nThe serialization format is:\n\n ::= \n (Note that may be empty, from the \"\" case in .)\n ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= \"+\" | \"-\" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei\n (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html)\n ::= m | \"\" | k | M | G | T | P | E\n (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.)\n ::= \"e\" | \"E\" \n\nNo matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities.\n\nWhen a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized.\n\nBefore serializing, Quantity will be put in \"canonical form\". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that:\n a. No precision is lost\n b. No fractional digits will be emitted\n c. The exponent (or suffix) is as large as possible.\nThe sign will be omitted unless the number is negative.\n\nExamples:\n 1.5 will be serialized as \"1500m\"\n 1.5Gi will be serialized as \"1536Mi\"\n\nNote that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise.\n\nNon-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.)\n\nThis format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation." + description: |- + Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors. + + The serialization format is: + + ::= + (Note that may be empty, from the "" case in .) + ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= "+" | "-" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei + (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html) + ::= m | "" | k | M | G | T | P | E + (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.) + ::= "e" | "E" + + No matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities. + + When a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized. + + Before serializing, Quantity will be put in "canonical form". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that: + a. No precision is lost + b. No fractional digits will be emitted + c. The exponent (or suffix) is as large as possible. + The sign will be omitted unless the number is negative. + + Examples: + 1.5 will be serialized as "1500m" + 1.5Gi will be serialized as "1536Mi" + + Note that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise. + + Non-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.) + + This format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation. nullable: true type: string selectors: @@ -87,16 +211,16 @@ spec: matchExpressions: description: matchExpressions is a list of label selector requirements. The requirements are ANDed. items: - description: "A label selector requirement is a selector that contains values, a key, and an operator that relates the key and values." + description: A label selector requirement is a selector that contains values, a key, and an operator that relates the key and values. properties: key: description: key is the label key that the selector applies to. type: string operator: - description: "operator represents a key's relationship to a set of values. Valid operators are In, NotIn, Exists and DoesNotExist." + description: operator represents a key's relationship to a set of values. Valid operators are In, NotIn, Exists and DoesNotExist. type: string values: - description: "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." + description: 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. items: type: string type: array @@ -108,7 +232,7 @@ spec: matchLabels: additionalProperties: type: string - description: "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." + description: 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. type: object type: object storageClass: @@ -144,33 +268,126 @@ spec: resources: default: memory: - limit: ~ + limit: null runtimeLimits: {} cpu: - min: ~ - max: ~ + min: null + max: null storage: logDirs: - capacity: ~ + capacity: null properties: cpu: default: - min: ~ - max: ~ + min: null + max: null properties: max: - description: "Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors.\n\nThe serialization format is:\n\n ::= \n (Note that may be empty, from the \"\" case in .)\n ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= \"+\" | \"-\" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei\n (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html)\n ::= m | \"\" | k | M | G | T | P | E\n (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.)\n ::= \"e\" | \"E\" \n\nNo matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities.\n\nWhen a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized.\n\nBefore serializing, Quantity will be put in \"canonical form\". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that:\n a. No precision is lost\n b. No fractional digits will be emitted\n c. The exponent (or suffix) is as large as possible.\nThe sign will be omitted unless the number is negative.\n\nExamples:\n 1.5 will be serialized as \"1500m\"\n 1.5Gi will be serialized as \"1536Mi\"\n\nNote that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise.\n\nNon-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.)\n\nThis format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation." + description: |- + Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors. + + The serialization format is: + + ::= + (Note that may be empty, from the "" case in .) + ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= "+" | "-" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei + (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html) + ::= m | "" | k | M | G | T | P | E + (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.) + ::= "e" | "E" + + No matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities. + + When a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized. + + Before serializing, Quantity will be put in "canonical form". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that: + a. No precision is lost + b. No fractional digits will be emitted + c. The exponent (or suffix) is as large as possible. + The sign will be omitted unless the number is negative. + + Examples: + 1.5 will be serialized as "1500m" + 1.5Gi will be serialized as "1536Mi" + + Note that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise. + + Non-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.) + + This format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation. nullable: true type: string min: - description: "Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors.\n\nThe serialization format is:\n\n ::= \n (Note that may be empty, from the \"\" case in .)\n ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= \"+\" | \"-\" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei\n (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html)\n ::= m | \"\" | k | M | G | T | P | E\n (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.)\n ::= \"e\" | \"E\" \n\nNo matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities.\n\nWhen a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized.\n\nBefore serializing, Quantity will be put in \"canonical form\". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that:\n a. No precision is lost\n b. No fractional digits will be emitted\n c. The exponent (or suffix) is as large as possible.\nThe sign will be omitted unless the number is negative.\n\nExamples:\n 1.5 will be serialized as \"1500m\"\n 1.5Gi will be serialized as \"1536Mi\"\n\nNote that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise.\n\nNon-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.)\n\nThis format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation." + description: |- + Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors. + + The serialization format is: + + ::= + (Note that may be empty, from the "" case in .) + ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= "+" | "-" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei + (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html) + ::= m | "" | k | M | G | T | P | E + (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.) + ::= "e" | "E" + + No matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities. + + When a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized. + + Before serializing, Quantity will be put in "canonical form". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that: + a. No precision is lost + b. No fractional digits will be emitted + c. The exponent (or suffix) is as large as possible. + The sign will be omitted unless the number is negative. + + Examples: + 1.5 will be serialized as "1500m" + 1.5Gi will be serialized as "1536Mi" + + Note that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise. + + Non-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.) + + This format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation. nullable: true type: string type: object memory: properties: limit: - description: "Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors.\n\nThe serialization format is:\n\n ::= \n (Note that may be empty, from the \"\" case in .)\n ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= \"+\" | \"-\" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei\n (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html)\n ::= m | \"\" | k | M | G | T | P | E\n (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.)\n ::= \"e\" | \"E\" \n\nNo matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities.\n\nWhen a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized.\n\nBefore serializing, Quantity will be put in \"canonical form\". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that:\n a. No precision is lost\n b. No fractional digits will be emitted\n c. The exponent (or suffix) is as large as possible.\nThe sign will be omitted unless the number is negative.\n\nExamples:\n 1.5 will be serialized as \"1500m\"\n 1.5Gi will be serialized as \"1536Mi\"\n\nNote that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise.\n\nNon-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.)\n\nThis format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation." + description: |- + Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors. + + The serialization format is: + + ::= + (Note that may be empty, from the "" case in .) + ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= "+" | "-" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei + (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html) + ::= m | "" | k | M | G | T | P | E + (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.) + ::= "e" | "E" + + No matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities. + + When a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized. + + Before serializing, Quantity will be put in "canonical form". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that: + a. No precision is lost + b. No fractional digits will be emitted + c. The exponent (or suffix) is as large as possible. + The sign will be omitted unless the number is negative. + + Examples: + 1.5 will be serialized as "1500m" + 1.5Gi will be serialized as "1536Mi" + + Note that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise. + + Non-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.) + + This format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation. nullable: true type: string runtimeLimits: @@ -180,10 +397,41 @@ spec: properties: logDirs: default: - capacity: ~ + capacity: null properties: capacity: - description: "Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors.\n\nThe serialization format is:\n\n ::= \n (Note that may be empty, from the \"\" case in .)\n ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= \"+\" | \"-\" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei\n (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html)\n ::= m | \"\" | k | M | G | T | P | E\n (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.)\n ::= \"e\" | \"E\" \n\nNo matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities.\n\nWhen a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized.\n\nBefore serializing, Quantity will be put in \"canonical form\". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that:\n a. No precision is lost\n b. No fractional digits will be emitted\n c. The exponent (or suffix) is as large as possible.\nThe sign will be omitted unless the number is negative.\n\nExamples:\n 1.5 will be serialized as \"1500m\"\n 1.5Gi will be serialized as \"1536Mi\"\n\nNote that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise.\n\nNon-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.)\n\nThis format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation." + description: |- + Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors. + + The serialization format is: + + ::= + (Note that may be empty, from the "" case in .) + ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= "+" | "-" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei + (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html) + ::= m | "" | k | M | G | T | P | E + (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.) + ::= "e" | "E" + + No matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities. + + When a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized. + + Before serializing, Quantity will be put in "canonical form". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that: + a. No precision is lost + b. No fractional digits will be emitted + c. The exponent (or suffix) is as large as possible. + The sign will be omitted unless the number is negative. + + Examples: + 1.5 will be serialized as "1500m" + 1.5Gi will be serialized as "1536Mi" + + Note that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise. + + Non-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.) + + This format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation. nullable: true type: string selectors: @@ -193,16 +441,16 @@ spec: matchExpressions: description: matchExpressions is a list of label selector requirements. The requirements are ANDed. items: - description: "A label selector requirement is a selector that contains values, a key, and an operator that relates the key and values." + description: A label selector requirement is a selector that contains values, a key, and an operator that relates the key and values. properties: key: description: key is the label key that the selector applies to. type: string operator: - description: "operator represents a key's relationship to a set of values. Valid operators are In, NotIn, Exists and DoesNotExist." + description: operator represents a key's relationship to a set of values. Valid operators are In, NotIn, Exists and DoesNotExist. type: string values: - description: "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." + description: 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. items: type: string type: array @@ -214,7 +462,7 @@ spec: matchLabels: additionalProperties: type: string - description: "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." + description: 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. type: object type: object storageClass: @@ -248,16 +496,16 @@ spec: matchExpressions: description: matchExpressions is a list of label selector requirements. The requirements are ANDed. items: - description: "A label selector requirement is a selector that contains values, a key, and an operator that relates the key and values." + description: A label selector requirement is a selector that contains values, a key, and an operator that relates the key and values. properties: key: description: key is the label key that the selector applies to. type: string operator: - description: "operator represents a key's relationship to a set of values. Valid operators are In, NotIn, Exists and DoesNotExist." + description: operator represents a key's relationship to a set of values. Valid operators are In, NotIn, Exists and DoesNotExist. type: string values: - description: "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." + description: 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. items: type: string type: array @@ -269,7 +517,7 @@ spec: matchLabels: additionalProperties: type: string - description: "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." + description: 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. type: object type: object type: object @@ -285,7 +533,7 @@ spec: secretClass: tls properties: clientAuthentication: - description: "Only affects client connections. This setting controls: - If clients need to authenticate themselves against the server via TLS - Which ca.crt to use when validating the provided client certs Defaults to `None`" + description: 'Only affects client connections. This setting controls: - If clients need to authenticate themselves against the server via TLS - Which ca.crt to use when validating the provided client certs Defaults to `None`' nullable: true properties: authenticationClass: @@ -296,7 +544,7 @@ spec: internalTls: default: secretClass: tls - description: "Only affects internal communication. Use mutual verification between Kafka nodes This setting controls: - Which cert the servers should use to authenticate themselves against other servers - Which ca.crt to use when validating the other server" + description: 'Only affects internal communication. Use mutual verification between Kafka nodes This setting controls: - Which cert the servers should use to authenticate themselves against other servers - Which ca.crt to use when validating the other server' nullable: true properties: secretClass: @@ -307,7 +555,7 @@ spec: tls: default: secretClass: tls - description: "Only affects client connections. This setting controls: - If TLS encryption is used at all - Which cert the servers should use to authenticate themselves against the client Defaults to `TlsSecretClass` { secret_class: \"tls\".to_string() }." + description: 'Only affects client connections. This setting controls: - If TLS encryption is used at all - Which cert the servers should use to authenticate themselves against the client Defaults to `TlsSecretClass` { secret_class: "tls".to_string() }.' nullable: true properties: secretClass: diff --git a/deploy/manifests/crds.yaml b/deploy/manifests/crds.yaml index 19abd657..e69a047e 100644 --- a/deploy/manifests/crds.yaml +++ b/deploy/manifests/crds.yaml @@ -21,7 +21,7 @@ spec: name: v1alpha1 schema: openAPIV3Schema: - description: "Auto-generated derived type for KafkaClusterSpec via `CustomResource`" + description: Auto-generated derived type for KafkaClusterSpec via `CustomResource` properties: spec: properties: @@ -39,33 +39,126 @@ spec: resources: default: memory: - limit: ~ + limit: null runtimeLimits: {} cpu: - min: ~ - max: ~ + min: null + max: null storage: logDirs: - capacity: ~ + capacity: null properties: cpu: default: - min: ~ - max: ~ + min: null + max: null properties: max: - description: "Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors.\n\nThe serialization format is:\n\n ::= \n (Note that may be empty, from the \"\" case in .)\n ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= \"+\" | \"-\" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei\n (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html)\n ::= m | \"\" | k | M | G | T | P | E\n (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.)\n ::= \"e\" | \"E\" \n\nNo matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities.\n\nWhen a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized.\n\nBefore serializing, Quantity will be put in \"canonical form\". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that:\n a. No precision is lost\n b. No fractional digits will be emitted\n c. The exponent (or suffix) is as large as possible.\nThe sign will be omitted unless the number is negative.\n\nExamples:\n 1.5 will be serialized as \"1500m\"\n 1.5Gi will be serialized as \"1536Mi\"\n\nNote that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise.\n\nNon-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.)\n\nThis format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation." + description: |- + Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors. + + The serialization format is: + + ::= + (Note that may be empty, from the "" case in .) + ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= "+" | "-" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei + (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html) + ::= m | "" | k | M | G | T | P | E + (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.) + ::= "e" | "E" + + No matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities. + + When a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized. + + Before serializing, Quantity will be put in "canonical form". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that: + a. No precision is lost + b. No fractional digits will be emitted + c. The exponent (or suffix) is as large as possible. + The sign will be omitted unless the number is negative. + + Examples: + 1.5 will be serialized as "1500m" + 1.5Gi will be serialized as "1536Mi" + + Note that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise. + + Non-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.) + + This format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation. nullable: true type: string min: - description: "Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors.\n\nThe serialization format is:\n\n ::= \n (Note that may be empty, from the \"\" case in .)\n ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= \"+\" | \"-\" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei\n (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html)\n ::= m | \"\" | k | M | G | T | P | E\n (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.)\n ::= \"e\" | \"E\" \n\nNo matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities.\n\nWhen a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized.\n\nBefore serializing, Quantity will be put in \"canonical form\". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that:\n a. No precision is lost\n b. No fractional digits will be emitted\n c. The exponent (or suffix) is as large as possible.\nThe sign will be omitted unless the number is negative.\n\nExamples:\n 1.5 will be serialized as \"1500m\"\n 1.5Gi will be serialized as \"1536Mi\"\n\nNote that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise.\n\nNon-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.)\n\nThis format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation." + description: |- + Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors. + + The serialization format is: + + ::= + (Note that may be empty, from the "" case in .) + ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= "+" | "-" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei + (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html) + ::= m | "" | k | M | G | T | P | E + (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.) + ::= "e" | "E" + + No matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities. + + When a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized. + + Before serializing, Quantity will be put in "canonical form". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that: + a. No precision is lost + b. No fractional digits will be emitted + c. The exponent (or suffix) is as large as possible. + The sign will be omitted unless the number is negative. + + Examples: + 1.5 will be serialized as "1500m" + 1.5Gi will be serialized as "1536Mi" + + Note that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise. + + Non-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.) + + This format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation. nullable: true type: string type: object memory: properties: limit: - description: "Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors.\n\nThe serialization format is:\n\n ::= \n (Note that may be empty, from the \"\" case in .)\n ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= \"+\" | \"-\" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei\n (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html)\n ::= m | \"\" | k | M | G | T | P | E\n (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.)\n ::= \"e\" | \"E\" \n\nNo matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities.\n\nWhen a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized.\n\nBefore serializing, Quantity will be put in \"canonical form\". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that:\n a. No precision is lost\n b. No fractional digits will be emitted\n c. The exponent (or suffix) is as large as possible.\nThe sign will be omitted unless the number is negative.\n\nExamples:\n 1.5 will be serialized as \"1500m\"\n 1.5Gi will be serialized as \"1536Mi\"\n\nNote that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise.\n\nNon-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.)\n\nThis format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation." + description: |- + Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors. + + The serialization format is: + + ::= + (Note that may be empty, from the "" case in .) + ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= "+" | "-" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei + (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html) + ::= m | "" | k | M | G | T | P | E + (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.) + ::= "e" | "E" + + No matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities. + + When a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized. + + Before serializing, Quantity will be put in "canonical form". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that: + a. No precision is lost + b. No fractional digits will be emitted + c. The exponent (or suffix) is as large as possible. + The sign will be omitted unless the number is negative. + + Examples: + 1.5 will be serialized as "1500m" + 1.5Gi will be serialized as "1536Mi" + + Note that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise. + + Non-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.) + + This format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation. nullable: true type: string runtimeLimits: @@ -75,10 +168,41 @@ spec: properties: logDirs: default: - capacity: ~ + capacity: null properties: capacity: - description: "Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors.\n\nThe serialization format is:\n\n ::= \n (Note that may be empty, from the \"\" case in .)\n ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= \"+\" | \"-\" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei\n (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html)\n ::= m | \"\" | k | M | G | T | P | E\n (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.)\n ::= \"e\" | \"E\" \n\nNo matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities.\n\nWhen a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized.\n\nBefore serializing, Quantity will be put in \"canonical form\". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that:\n a. No precision is lost\n b. No fractional digits will be emitted\n c. The exponent (or suffix) is as large as possible.\nThe sign will be omitted unless the number is negative.\n\nExamples:\n 1.5 will be serialized as \"1500m\"\n 1.5Gi will be serialized as \"1536Mi\"\n\nNote that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise.\n\nNon-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.)\n\nThis format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation." + description: |- + Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors. + + The serialization format is: + + ::= + (Note that may be empty, from the "" case in .) + ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= "+" | "-" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei + (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html) + ::= m | "" | k | M | G | T | P | E + (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.) + ::= "e" | "E" + + No matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities. + + When a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized. + + Before serializing, Quantity will be put in "canonical form". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that: + a. No precision is lost + b. No fractional digits will be emitted + c. The exponent (or suffix) is as large as possible. + The sign will be omitted unless the number is negative. + + Examples: + 1.5 will be serialized as "1500m" + 1.5Gi will be serialized as "1536Mi" + + Note that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise. + + Non-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.) + + This format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation. nullable: true type: string selectors: @@ -88,16 +212,16 @@ spec: matchExpressions: description: matchExpressions is a list of label selector requirements. The requirements are ANDed. items: - description: "A label selector requirement is a selector that contains values, a key, and an operator that relates the key and values." + description: A label selector requirement is a selector that contains values, a key, and an operator that relates the key and values. properties: key: description: key is the label key that the selector applies to. type: string operator: - description: "operator represents a key's relationship to a set of values. Valid operators are In, NotIn, Exists and DoesNotExist." + description: operator represents a key's relationship to a set of values. Valid operators are In, NotIn, Exists and DoesNotExist. type: string values: - description: "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." + description: 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. items: type: string type: array @@ -109,7 +233,7 @@ spec: matchLabels: additionalProperties: type: string - description: "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." + description: 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. type: object type: object storageClass: @@ -145,33 +269,126 @@ spec: resources: default: memory: - limit: ~ + limit: null runtimeLimits: {} cpu: - min: ~ - max: ~ + min: null + max: null storage: logDirs: - capacity: ~ + capacity: null properties: cpu: default: - min: ~ - max: ~ + min: null + max: null properties: max: - description: "Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors.\n\nThe serialization format is:\n\n ::= \n (Note that may be empty, from the \"\" case in .)\n ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= \"+\" | \"-\" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei\n (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html)\n ::= m | \"\" | k | M | G | T | P | E\n (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.)\n ::= \"e\" | \"E\" \n\nNo matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities.\n\nWhen a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized.\n\nBefore serializing, Quantity will be put in \"canonical form\". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that:\n a. No precision is lost\n b. No fractional digits will be emitted\n c. The exponent (or suffix) is as large as possible.\nThe sign will be omitted unless the number is negative.\n\nExamples:\n 1.5 will be serialized as \"1500m\"\n 1.5Gi will be serialized as \"1536Mi\"\n\nNote that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise.\n\nNon-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.)\n\nThis format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation." + description: |- + Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors. + + The serialization format is: + + ::= + (Note that may be empty, from the "" case in .) + ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= "+" | "-" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei + (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html) + ::= m | "" | k | M | G | T | P | E + (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.) + ::= "e" | "E" + + No matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities. + + When a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized. + + Before serializing, Quantity will be put in "canonical form". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that: + a. No precision is lost + b. No fractional digits will be emitted + c. The exponent (or suffix) is as large as possible. + The sign will be omitted unless the number is negative. + + Examples: + 1.5 will be serialized as "1500m" + 1.5Gi will be serialized as "1536Mi" + + Note that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise. + + Non-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.) + + This format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation. nullable: true type: string min: - description: "Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors.\n\nThe serialization format is:\n\n ::= \n (Note that may be empty, from the \"\" case in .)\n ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= \"+\" | \"-\" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei\n (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html)\n ::= m | \"\" | k | M | G | T | P | E\n (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.)\n ::= \"e\" | \"E\" \n\nNo matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities.\n\nWhen a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized.\n\nBefore serializing, Quantity will be put in \"canonical form\". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that:\n a. No precision is lost\n b. No fractional digits will be emitted\n c. The exponent (or suffix) is as large as possible.\nThe sign will be omitted unless the number is negative.\n\nExamples:\n 1.5 will be serialized as \"1500m\"\n 1.5Gi will be serialized as \"1536Mi\"\n\nNote that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise.\n\nNon-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.)\n\nThis format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation." + description: |- + Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors. + + The serialization format is: + + ::= + (Note that may be empty, from the "" case in .) + ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= "+" | "-" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei + (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html) + ::= m | "" | k | M | G | T | P | E + (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.) + ::= "e" | "E" + + No matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities. + + When a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized. + + Before serializing, Quantity will be put in "canonical form". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that: + a. No precision is lost + b. No fractional digits will be emitted + c. The exponent (or suffix) is as large as possible. + The sign will be omitted unless the number is negative. + + Examples: + 1.5 will be serialized as "1500m" + 1.5Gi will be serialized as "1536Mi" + + Note that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise. + + Non-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.) + + This format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation. nullable: true type: string type: object memory: properties: limit: - description: "Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors.\n\nThe serialization format is:\n\n ::= \n (Note that may be empty, from the \"\" case in .)\n ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= \"+\" | \"-\" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei\n (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html)\n ::= m | \"\" | k | M | G | T | P | E\n (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.)\n ::= \"e\" | \"E\" \n\nNo matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities.\n\nWhen a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized.\n\nBefore serializing, Quantity will be put in \"canonical form\". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that:\n a. No precision is lost\n b. No fractional digits will be emitted\n c. The exponent (or suffix) is as large as possible.\nThe sign will be omitted unless the number is negative.\n\nExamples:\n 1.5 will be serialized as \"1500m\"\n 1.5Gi will be serialized as \"1536Mi\"\n\nNote that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise.\n\nNon-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.)\n\nThis format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation." + description: |- + Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors. + + The serialization format is: + + ::= + (Note that may be empty, from the "" case in .) + ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= "+" | "-" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei + (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html) + ::= m | "" | k | M | G | T | P | E + (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.) + ::= "e" | "E" + + No matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities. + + When a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized. + + Before serializing, Quantity will be put in "canonical form". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that: + a. No precision is lost + b. No fractional digits will be emitted + c. The exponent (or suffix) is as large as possible. + The sign will be omitted unless the number is negative. + + Examples: + 1.5 will be serialized as "1500m" + 1.5Gi will be serialized as "1536Mi" + + Note that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise. + + Non-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.) + + This format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation. nullable: true type: string runtimeLimits: @@ -181,10 +398,41 @@ spec: properties: logDirs: default: - capacity: ~ + capacity: null properties: capacity: - description: "Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors.\n\nThe serialization format is:\n\n ::= \n (Note that may be empty, from the \"\" case in .)\n ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= \"+\" | \"-\" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei\n (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html)\n ::= m | \"\" | k | M | G | T | P | E\n (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.)\n ::= \"e\" | \"E\" \n\nNo matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities.\n\nWhen a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized.\n\nBefore serializing, Quantity will be put in \"canonical form\". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that:\n a. No precision is lost\n b. No fractional digits will be emitted\n c. The exponent (or suffix) is as large as possible.\nThe sign will be omitted unless the number is negative.\n\nExamples:\n 1.5 will be serialized as \"1500m\"\n 1.5Gi will be serialized as \"1536Mi\"\n\nNote that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise.\n\nNon-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.)\n\nThis format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation." + description: |- + Quantity is a fixed-point representation of a number. It provides convenient marshaling/unmarshaling in JSON and YAML, in addition to String() and AsInt64() accessors. + + The serialization format is: + + ::= + (Note that may be empty, from the "" case in .) + ::= 0 | 1 | ... | 9 ::= | ::= | . | . | . ::= "+" | "-" ::= | ::= | | ::= Ki | Mi | Gi | Ti | Pi | Ei + (International System of units; See: http://physics.nist.gov/cuu/Units/binary.html) + ::= m | "" | k | M | G | T | P | E + (Note that 1024 = 1Ki but 1000 = 1k; I didn't choose the capitalization.) + ::= "e" | "E" + + No matter which of the three exponent forms is used, no quantity may represent a number greater than 2^63-1 in magnitude, nor may it have more than 3 decimal places. Numbers larger or more precise will be capped or rounded up. (E.g.: 0.1m will rounded up to 1m.) This may be extended in the future if we require larger or smaller quantities. + + When a Quantity is parsed from a string, it will remember the type of suffix it had, and will use the same type again when it is serialized. + + Before serializing, Quantity will be put in "canonical form". This means that Exponent/suffix will be adjusted up or down (with a corresponding increase or decrease in Mantissa) such that: + a. No precision is lost + b. No fractional digits will be emitted + c. The exponent (or suffix) is as large as possible. + The sign will be omitted unless the number is negative. + + Examples: + 1.5 will be serialized as "1500m" + 1.5Gi will be serialized as "1536Mi" + + Note that the quantity will NEVER be internally represented by a floating point number. That is the whole point of this exercise. + + Non-canonical values will still parse as long as they are well formed, but will be re-emitted in their canonical form. (So always use canonical form, or don't diff.) + + This format is intended to make it difficult to use these numbers without writing some sort of special handling code in the hopes that that will cause implementors to also use a fixed point implementation. nullable: true type: string selectors: @@ -194,16 +442,16 @@ spec: matchExpressions: description: matchExpressions is a list of label selector requirements. The requirements are ANDed. items: - description: "A label selector requirement is a selector that contains values, a key, and an operator that relates the key and values." + description: A label selector requirement is a selector that contains values, a key, and an operator that relates the key and values. properties: key: description: key is the label key that the selector applies to. type: string operator: - description: "operator represents a key's relationship to a set of values. Valid operators are In, NotIn, Exists and DoesNotExist." + description: operator represents a key's relationship to a set of values. Valid operators are In, NotIn, Exists and DoesNotExist. type: string values: - description: "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." + description: 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. items: type: string type: array @@ -215,7 +463,7 @@ spec: matchLabels: additionalProperties: type: string - description: "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." + description: 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. type: object type: object storageClass: @@ -249,16 +497,16 @@ spec: matchExpressions: description: matchExpressions is a list of label selector requirements. The requirements are ANDed. items: - description: "A label selector requirement is a selector that contains values, a key, and an operator that relates the key and values." + description: A label selector requirement is a selector that contains values, a key, and an operator that relates the key and values. properties: key: description: key is the label key that the selector applies to. type: string operator: - description: "operator represents a key's relationship to a set of values. Valid operators are In, NotIn, Exists and DoesNotExist." + description: operator represents a key's relationship to a set of values. Valid operators are In, NotIn, Exists and DoesNotExist. type: string values: - description: "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." + description: 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. items: type: string type: array @@ -270,7 +518,7 @@ spec: matchLabels: additionalProperties: type: string - description: "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." + description: 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. type: object type: object type: object @@ -286,7 +534,7 @@ spec: secretClass: tls properties: clientAuthentication: - description: "Only affects client connections. This setting controls: - If clients need to authenticate themselves against the server via TLS - Which ca.crt to use when validating the provided client certs Defaults to `None`" + description: 'Only affects client connections. This setting controls: - If clients need to authenticate themselves against the server via TLS - Which ca.crt to use when validating the provided client certs Defaults to `None`' nullable: true properties: authenticationClass: @@ -297,7 +545,7 @@ spec: internalTls: default: secretClass: tls - description: "Only affects internal communication. Use mutual verification between Kafka nodes This setting controls: - Which cert the servers should use to authenticate themselves against other servers - Which ca.crt to use when validating the other server" + description: 'Only affects internal communication. Use mutual verification between Kafka nodes This setting controls: - Which cert the servers should use to authenticate themselves against other servers - Which ca.crt to use when validating the other server' nullable: true properties: secretClass: @@ -308,7 +556,7 @@ spec: tls: default: secretClass: tls - description: "Only affects client connections. This setting controls: - If TLS encryption is used at all - Which cert the servers should use to authenticate themselves against the client Defaults to `TlsSecretClass` { secret_class: \"tls\".to_string() }." + description: 'Only affects client connections. This setting controls: - If TLS encryption is used at all - Which cert the servers should use to authenticate themselves against the client Defaults to `TlsSecretClass` { secret_class: "tls".to_string() }.' nullable: true properties: secretClass: diff --git a/rust/crd/Cargo.toml b/rust/crd/Cargo.toml index 599f7672..4df8c0e9 100644 --- a/rust/crd/Cargo.toml +++ b/rust/crd/Cargo.toml @@ -8,7 +8,7 @@ repository = "https://github.com/stackabletech/kafka-operator" version = "0.8.0-nightly" [dependencies] -stackable-operator = { git = "https://github.com/stackabletech/operator-rs.git", tag = "0.22.0" } +stackable-operator = { git = "https://github.com/stackabletech/operator-rs.git", tag = "0.25.0" } semver = "1.0.14" serde = { version = "1.0.144", features = ["derive"] } diff --git a/rust/operator-binary/Cargo.toml b/rust/operator-binary/Cargo.toml index e84e7bff..ee8cb9dc 100644 --- a/rust/operator-binary/Cargo.toml +++ b/rust/operator-binary/Cargo.toml @@ -11,7 +11,7 @@ version = "0.8.0-nightly" [dependencies] stackable-kafka-crd = { path = "../crd" } stackable-kafka-operator = { path = "../operator" } -stackable-operator = { git = "https://github.com/stackabletech/operator-rs.git", tag = "0.22.0" } +stackable-operator = { git = "https://github.com/stackabletech/operator-rs.git", tag = "0.25.0" } clap = { version = "3.2.22", features = ["derive", "env"] } serde_yaml = "0.8.24" @@ -20,7 +20,7 @@ tracing = "0.1.36" [build-dependencies] built = { version = "0.5.1", features = ["chrono", "git2"] } -stackable-operator = { git = "https://github.com/stackabletech/operator-rs.git", tag = "0.22.0" } +stackable-operator = { git = "https://github.com/stackabletech/operator-rs.git", tag = "0.25.0" } stackable-kafka-crd = { path = "../crd" } [[bin]] diff --git a/rust/operator-binary/src/stackable-kafka-operator.rs b/rust/operator-binary/src/stackable-kafka-operator.rs index 2066b659..669ab6cd 100644 --- a/rust/operator-binary/src/stackable-kafka-operator.rs +++ b/rust/operator-binary/src/stackable-kafka-operator.rs @@ -3,8 +3,7 @@ use stackable_kafka_crd::{KafkaCluster, APP_NAME}; use stackable_kafka_operator::ControllerConfig; use stackable_operator::{ cli::{Command, ProductOperatorRun}, - client, error, - kube::CustomResourceExt, + client, error, CustomResourceExt, }; mod built_info { @@ -31,7 +30,7 @@ struct KafkaRun { async fn main() -> Result<(), error::Error> { let opts = Opts::parse(); match opts.cmd { - Command::Crd => println!("{}", serde_yaml::to_string(&KafkaCluster::crd())?), + Command::Crd => KafkaCluster::print_yaml_schema()?, Command::Run(KafkaRun { kafka_broker_clusterrole, common: diff --git a/rust/operator/Cargo.toml b/rust/operator/Cargo.toml index 3e94541e..66967e52 100644 --- a/rust/operator/Cargo.toml +++ b/rust/operator/Cargo.toml @@ -9,7 +9,7 @@ version = "0.8.0-nightly" [dependencies] stackable-kafka-crd = { path = "../crd" } -stackable-operator = { git = "https://github.com/stackabletech/operator-rs.git", tag = "0.22.0" } +stackable-operator = { git = "https://github.com/stackabletech/operator-rs.git", tag = "0.25.0" } futures = "0.3.24" serde = { version = "1.0.144", features = ["derive"] } diff --git a/rust/operator/src/discovery.rs b/rust/operator/src/discovery.rs index a1734dce..3eb51b50 100644 --- a/rust/operator/src/discovery.rs +++ b/rust/operator/src/discovery.rs @@ -8,6 +8,8 @@ use stackable_operator::{ kube::{runtime::reflector::ObjectRef, Resource, ResourceExt}, }; +use crate::kafka_controller::CONTROLLER_NAME; + #[derive(Snafu, Debug)] pub enum Error { #[snafu(display("object {} is missing metadata to build owner reference", kafka))] @@ -45,7 +47,7 @@ pub async fn build_discovery_configmaps( kafka: &KafkaCluster, svc: &Service, ) -> Result, Error> { - let name = owner.name(); + let name = owner.name_any(); let port_name = kafka.client_port_name(); Ok(vec![ build_discovery_configmap(&name, owner, kafka, service_hosts(svc, port_name)?)?, @@ -89,6 +91,7 @@ fn build_discovery_configmap( kafka .image_version() .context(KafkaVersionParseFailureSnafu)?, + CONTROLLER_NAME, &KafkaRole::Broker.to_string(), "discovery", ) diff --git a/rust/operator/src/kafka_controller.rs b/rust/operator/src/kafka_controller.rs index 0369f5e1..5ca5933f 100644 --- a/rust/operator/src/kafka_controller.rs +++ b/rust/operator/src/kafka_controller.rs @@ -61,7 +61,7 @@ use crate::{ ControllerConfig, }; -const FIELD_MANAGER_SCOPE: &str = "kafkacluster"; +pub const CONTROLLER_NAME: &str = "kafka-operator"; pub struct Ctx { pub client: stackable_operator::client::Client, @@ -292,16 +292,12 @@ pub async fn reconcile_kafka(kafka: Arc, ctx: Arc) -> Result< build_broker_role_serviceaccount(&kafka, &ctx.controller_config)?; let broker_role_serviceaccount_ref = ObjectRef::from_obj(&broker_role_serviceaccount); let broker_role_service = client - .apply_patch( - FIELD_MANAGER_SCOPE, - &broker_role_service, - &broker_role_service, - ) + .apply_patch(CONTROLLER_NAME, &broker_role_service, &broker_role_service) .await .context(ApplyRoleServiceSnafu)?; client .apply_patch( - FIELD_MANAGER_SCOPE, + CONTROLLER_NAME, &broker_role_serviceaccount, &broker_role_serviceaccount, ) @@ -309,7 +305,7 @@ pub async fn reconcile_kafka(kafka: Arc, ctx: Arc) -> Result< .context(ApplyRoleServiceAccountSnafu)?; client .apply_patch( - FIELD_MANAGER_SCOPE, + CONTROLLER_NAME, &broker_role_rolebinding, &broker_role_rolebinding, ) @@ -330,19 +326,19 @@ pub async fn reconcile_kafka(kafka: Arc, ctx: Arc) -> Result< client_authentication_class.as_ref(), )?; client - .apply_patch(FIELD_MANAGER_SCOPE, &rg_service, &rg_service) + .apply_patch(CONTROLLER_NAME, &rg_service, &rg_service) .await .with_context(|_| ApplyRoleGroupServiceSnafu { rolegroup: rolegroup.clone(), })?; client - .apply_patch(FIELD_MANAGER_SCOPE, &rg_configmap, &rg_configmap) + .apply_patch(CONTROLLER_NAME, &rg_configmap, &rg_configmap) .await .with_context(|_| ApplyRoleGroupConfigSnafu { rolegroup: rolegroup.clone(), })?; client - .apply_patch(FIELD_MANAGER_SCOPE, &rg_statefulset, &rg_statefulset) + .apply_patch(CONTROLLER_NAME, &rg_statefulset, &rg_statefulset) .await .with_context(|_| ApplyRoleGroupStatefulSetSnafu { rolegroup: rolegroup.clone(), @@ -354,7 +350,7 @@ pub async fn reconcile_kafka(kafka: Arc, ctx: Arc) -> Result< .context(BuildDiscoveryConfigSnafu)? { client - .apply_patch(FIELD_MANAGER_SCOPE, &discovery_cm, &discovery_cm) + .apply_patch(CONTROLLER_NAME, &discovery_cm, &discovery_cm) .await .context(ApplyDiscoveryConfigSnafu)?; } @@ -381,6 +377,7 @@ pub fn build_broker_role_service(kafka: &KafkaCluster) -> Result { kafka .image_version() .context(KafkaVersionParseFailureSnafu)?, + CONTROLLER_NAME, &role_name, "global", ) @@ -413,6 +410,7 @@ fn build_broker_role_serviceaccount( kafka .image_version() .context(KafkaVersionParseFailureSnafu)?, + CONTROLLER_NAME, &role_name, "global", ) @@ -432,6 +430,7 @@ fn build_broker_role_serviceaccount( kafka .image_version() .context(KafkaVersionParseFailureSnafu)?, + CONTROLLER_NAME, &role_name, "global", ) @@ -478,6 +477,7 @@ fn build_broker_rolegroup_config_map( kafka .image_version() .context(KafkaVersionParseFailureSnafu)?, + CONTROLLER_NAME, &rolegroup.role, &rolegroup.role_group, ) @@ -520,6 +520,7 @@ fn build_broker_rolegroup_service( kafka .image_version() .context(KafkaVersionParseFailureSnafu)?, + CONTROLLER_NAME, &rolegroup.role, &rolegroup.role_group, ) @@ -552,9 +553,10 @@ fn build_broker_rolegroup_statefulset( opa_connect_string: Option<&str>, client_authentication_class: Option<&AuthenticationClass>, ) -> Result { - let mut cb_kafka = ContainerBuilder::new(APP_NAME); - let mut cb_prepare = ContainerBuilder::new("prepare"); - let mut cb_kcat_prober = ContainerBuilder::new("kcat-prober"); + let mut cb_kafka = ContainerBuilder::new(APP_NAME).expect("ContainerBuilder not created"); + let mut cb_prepare = ContainerBuilder::new("prepare").expect("ContainerBuilder not created"); + let mut cb_kcat_prober = + ContainerBuilder::new("kcat-prober").expect("ContainerBuilder not created"); let mut pod_builder = PodBuilder::new(); let role = kafka.spec.brokers.as_ref().context(NoBrokerRoleSnafu)?; @@ -621,6 +623,7 @@ fn build_broker_rolegroup_statefulset( } let container_get_svc = ContainerBuilder::new("get-svc") + .expect("ContainerBuilder not created") .image("docker.stackable.tech/stackable/tools:0.2.0-stackable0.3.0") .command(vec!["bash".to_string()]) .args(vec![ @@ -793,6 +796,7 @@ fn build_broker_rolegroup_statefulset( kafka, APP_NAME, image_version, + CONTROLLER_NAME, &rolegroup_ref.role, &rolegroup_ref.role_group, ) @@ -835,6 +839,7 @@ fn build_broker_rolegroup_statefulset( kafka, APP_NAME, image_version, + CONTROLLER_NAME, &rolegroup_ref.role, &rolegroup_ref.role_group, ) From f63b8620295af134354080f018512290467c4283 Mon Sep 17 00:00:00 2001 From: Sebastian Bernauer Date: Mon, 26 Sep 2022 15:43:32 +0200 Subject: [PATCH 02/19] WIP, first try --- Cargo.lock | 23 +++++++----------- deploy/crd/kafkacluster.crd.yaml | 29 ++++++++++++++++++++--- rust/crd/Cargo.toml | 2 +- rust/crd/src/lib.rs | 26 +++++++++----------- rust/operator-binary/Cargo.toml | 4 ++-- rust/operator/Cargo.toml | 2 +- rust/operator/src/discovery.rs | 4 +--- rust/operator/src/kafka_controller.rs | 34 +++++++-------------------- 8 files changed, 60 insertions(+), 64 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 642882f4..137212af 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -841,8 +841,7 @@ dependencies = [ [[package]] name = "kube" version = "0.74.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a527a8001a61d8d470dab27ac650889938760c243903e7cd90faaf7c60a34bdd" +source = "git+https://github.com/sbernauer/kube.git?branch=release-0.74.0#ed443df05f9dfd34ab35799f696730e081b4742f" dependencies = [ "k8s-openapi", "kube-client", @@ -854,8 +853,7 @@ dependencies = [ [[package]] name = "kube-client" version = "0.74.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c0d48f42df4e8342e9f488c4b97e3759d0042c4e7ab1a853cc285adb44409480" +source = "git+https://github.com/sbernauer/kube.git?branch=release-0.74.0#ed443df05f9dfd34ab35799f696730e081b4742f" dependencies = [ "base64", "bytes", @@ -891,8 +889,7 @@ dependencies = [ [[package]] name = "kube-core" version = "0.74.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "91f56027f862fdcad265d2e9616af416a355e28a1c620bb709083494753e070d" +source = "git+https://github.com/sbernauer/kube.git?branch=release-0.74.0#ed443df05f9dfd34ab35799f696730e081b4742f" dependencies = [ "chrono", "form_urlencoded", @@ -909,8 +906,7 @@ dependencies = [ [[package]] name = "kube-derive" version = "0.74.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "66d74121eb41af4480052901f31142d8d9bbdf1b7c6b856da43bcb02f5b1b177" +source = "git+https://github.com/sbernauer/kube.git?branch=release-0.74.0#ed443df05f9dfd34ab35799f696730e081b4742f" dependencies = [ "darling", "proc-macro2", @@ -922,8 +918,7 @@ dependencies = [ [[package]] name = "kube-runtime" version = "0.74.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8fdcf5a20f968768e342ef1a457491bb5661fccd81119666d626c57500b16d99" +source = "git+https://github.com/sbernauer/kube.git?branch=release-0.74.0#ed443df05f9dfd34ab35799f696730e081b4742f" dependencies = [ "ahash", "backoff", @@ -1713,8 +1708,8 @@ dependencies = [ [[package]] name = "stackable-operator" -version = "0.25.0" -source = "git+https://github.com/stackabletech/operator-rs.git?tag=0.25.0#490ef77e05d86a0bc2b555fd5950593d9f3a5d4b" +version = "0.25.1" +source = "git+https://github.com/stackabletech/operator-rs.git?branch=feature/product-image-selection#ce854e828b3b7900fec55661bbb805534349e506" dependencies = [ "chrono", "clap", @@ -1746,8 +1741,8 @@ dependencies = [ [[package]] name = "stackable-operator-derive" -version = "0.25.0" -source = "git+https://github.com/stackabletech/operator-rs.git?tag=0.25.0#490ef77e05d86a0bc2b555fd5950593d9f3a5d4b" +version = "0.25.1" +source = "git+https://github.com/stackabletech/operator-rs.git?branch=feature/product-image-selection#ce854e828b3b7900fec55661bbb805534349e506" dependencies = [ "darling", "proc-macro2", diff --git a/deploy/crd/kafkacluster.crd.yaml b/deploy/crd/kafkacluster.crd.yaml index 4f4fa65b..c48e49ca 100644 --- a/deploy/crd/kafkacluster.crd.yaml +++ b/deploy/crd/kafkacluster.crd.yaml @@ -562,6 +562,31 @@ spec: - secretClass type: object type: object + image: + anyOf: + - required: + - custom + - productVersion + - required: + - productVersion + - stackableVersion + - required: + - productVersion + properties: + custom: + description: Overwrite the docker image. Specify the full docker image name, e.g. `docker.stackable.tech/stackable/superset:1.4.1-stackable2.1.0` + type: string + productVersion: + description: Version of the product, e.g. `1.4.1`. + type: string + repo: + description: Name of the docker repo, e.g. `docker.stackable.tech/stackable` + nullable: true + type: string + stackableVersion: + description: Stackable version of the product, e.g. 2.1.0 + type: string + type: object log4j: nullable: true type: string @@ -579,12 +604,10 @@ spec: stopped: nullable: true type: boolean - version: - nullable: true - type: string zookeeperConfigMapName: type: string required: + - image - zookeeperConfigMapName type: object required: diff --git a/rust/crd/Cargo.toml b/rust/crd/Cargo.toml index 4df8c0e9..cd1a01b3 100644 --- a/rust/crd/Cargo.toml +++ b/rust/crd/Cargo.toml @@ -8,7 +8,7 @@ repository = "https://github.com/stackabletech/kafka-operator" version = "0.8.0-nightly" [dependencies] -stackable-operator = { git = "https://github.com/stackabletech/operator-rs.git", tag = "0.25.0" } +stackable-operator = { git = "https://github.com/stackabletech/operator-rs.git", branch = "feature/product-image-selection" } semver = "1.0.14" serde = { version = "1.0.144", features = ["derive"] } diff --git a/rust/crd/src/lib.rs b/rust/crd/src/lib.rs index 38d22c05..b0b57984 100644 --- a/rust/crd/src/lib.rs +++ b/rust/crd/src/lib.rs @@ -2,6 +2,7 @@ pub mod listener; use serde::{Deserialize, Serialize}; use snafu::{OptionExt, Snafu}; +use stackable_operator::commons::product_image_selection::ProductImageSelection; use stackable_operator::memory::to_java_heap; use stackable_operator::{ commons::{ @@ -22,6 +23,7 @@ use stackable_operator::{ use std::collections::BTreeMap; use strum::{Display, EnumIter, EnumString}; +pub const DOCKER_IMAGE_BASE_NAME: &str = "kafka"; pub const APP_NAME: &str = "kafka"; // ports pub const CLIENT_PORT_NAME: &str = "kafka"; @@ -113,7 +115,7 @@ pub enum Error { )] #[serde(rename_all = "camelCase")] pub struct KafkaClusterSpec { - pub version: Option, + pub image: ProductImageSelection, pub brokers: Option>, pub zookeeper_config_map_name: String, pub opa: Option, @@ -298,23 +300,17 @@ impl KafkaCluster { .transpose() } - /// Returns the provided docker image e.g. 2.8.1-stackable0.1.0. - pub fn image_version(&self) -> Result<&str, Error> { + /// Returns the product version, e.g. `2.1.0` + pub fn product_version(&self) -> String { self.spec - .version - .as_deref() - .context(ObjectHasNoVersionSnafu) + .image + .resolve(DOCKER_IMAGE_BASE_NAME) + .product_version } - /// Returns our semver representation for product config e.g. 2.8.1. - pub fn product_version(&self) -> Result<&str, Error> { - let image_version = self.image_version()?; - image_version - .split('-') - .next() - .with_context(|| KafkaProductVersionSnafu { - image_version: image_version.to_string(), - }) + /// Returns the full image name e.g. `docker.stackable.tech/stackable/superset:1.4.1-stackable2.1.0` + pub fn image(&self) -> String { + self.spec.image.resolve(DOCKER_IMAGE_BASE_NAME).image } /// Returns the secret class for client connection encryption. Defaults to `tls`. diff --git a/rust/operator-binary/Cargo.toml b/rust/operator-binary/Cargo.toml index ee8cb9dc..0209abf8 100644 --- a/rust/operator-binary/Cargo.toml +++ b/rust/operator-binary/Cargo.toml @@ -11,7 +11,7 @@ version = "0.8.0-nightly" [dependencies] stackable-kafka-crd = { path = "../crd" } stackable-kafka-operator = { path = "../operator" } -stackable-operator = { git = "https://github.com/stackabletech/operator-rs.git", tag = "0.25.0" } +stackable-operator = { git = "https://github.com/stackabletech/operator-rs.git", branch = "feature/product-image-selection" } clap = { version = "3.2.22", features = ["derive", "env"] } serde_yaml = "0.8.24" @@ -20,7 +20,7 @@ tracing = "0.1.36" [build-dependencies] built = { version = "0.5.1", features = ["chrono", "git2"] } -stackable-operator = { git = "https://github.com/stackabletech/operator-rs.git", tag = "0.25.0" } +stackable-operator = { git = "https://github.com/stackabletech/operator-rs.git", branch = "feature/product-image-selection" } stackable-kafka-crd = { path = "../crd" } [[bin]] diff --git a/rust/operator/Cargo.toml b/rust/operator/Cargo.toml index 66967e52..42a797eb 100644 --- a/rust/operator/Cargo.toml +++ b/rust/operator/Cargo.toml @@ -9,7 +9,7 @@ version = "0.8.0-nightly" [dependencies] stackable-kafka-crd = { path = "../crd" } -stackable-operator = { git = "https://github.com/stackabletech/operator-rs.git", tag = "0.25.0" } +stackable-operator = { git = "https://github.com/stackabletech/operator-rs.git", branch = "feature/product-image-selection" } futures = "0.3.24" serde = { version = "1.0.144", features = ["derive"] } diff --git a/rust/operator/src/discovery.rs b/rust/operator/src/discovery.rs index 3eb51b50..e836223d 100644 --- a/rust/operator/src/discovery.rs +++ b/rust/operator/src/discovery.rs @@ -88,9 +88,7 @@ fn build_discovery_configmap( .with_recommended_labels( kafka, APP_NAME, - kafka - .image_version() - .context(KafkaVersionParseFailureSnafu)?, + &kafka.product_version(), CONTROLLER_NAME, &KafkaRole::Broker.to_string(), "discovery", diff --git a/rust/operator/src/kafka_controller.rs b/rust/operator/src/kafka_controller.rs index 5ca5933f..8813675e 100644 --- a/rust/operator/src/kafka_controller.rs +++ b/rust/operator/src/kafka_controller.rs @@ -226,9 +226,7 @@ pub async fn reconcile_kafka(kafka: Arc, ctx: Arc) -> Result< let client = &ctx.client; let validated_config = validate_all_roles_and_groups_config( - kafka - .product_version() - .context(KafkaVersionParseFailureSnafu)?, + &kafka.product_version(), &transform_all_roles_to_config( &*kafka, [( @@ -374,9 +372,7 @@ pub fn build_broker_role_service(kafka: &KafkaCluster) -> Result { .with_recommended_labels( kafka, APP_NAME, - kafka - .image_version() - .context(KafkaVersionParseFailureSnafu)?, + &kafka.product_version(), CONTROLLER_NAME, &role_name, "global", @@ -407,9 +403,7 @@ fn build_broker_role_serviceaccount( .with_recommended_labels( kafka, APP_NAME, - kafka - .image_version() - .context(KafkaVersionParseFailureSnafu)?, + &kafka.product_version(), CONTROLLER_NAME, &role_name, "global", @@ -427,9 +421,7 @@ fn build_broker_role_serviceaccount( .with_recommended_labels( kafka, APP_NAME, - kafka - .image_version() - .context(KafkaVersionParseFailureSnafu)?, + &kafka.product_version(), CONTROLLER_NAME, &role_name, "global", @@ -474,9 +466,7 @@ fn build_broker_rolegroup_config_map( .with_recommended_labels( kafka, APP_NAME, - kafka - .image_version() - .context(KafkaVersionParseFailureSnafu)?, + &kafka.product_version(), CONTROLLER_NAME, &rolegroup.role, &rolegroup.role_group, @@ -517,9 +507,7 @@ fn build_broker_rolegroup_service( .with_recommended_labels( kafka, APP_NAME, - kafka - .image_version() - .context(KafkaVersionParseFailureSnafu)?, + &kafka.product_version(), CONTROLLER_NAME, &rolegroup.role, &rolegroup.role_group, @@ -566,10 +554,6 @@ fn build_broker_rolegroup_statefulset( .with_context(|| RoleGroupNotFoundSnafu { rolegroup: rolegroup_ref.clone(), })?; - let image_version = kafka - .image_version() - .context(KafkaVersionParseFailureSnafu)?; - let image = format!("docker.stackable.tech/stackable/kafka:{}", image_version); let get_svc_args = get_svc_container_cmd_args(kafka); @@ -749,7 +733,7 @@ fn build_broker_rolegroup_statefulset( }); cb_kafka - .image(image) + .image(kafka.image()) .args(vec![ "sh".to_string(), "-c".to_string(), @@ -795,7 +779,7 @@ fn build_broker_rolegroup_statefulset( m.with_recommended_labels( kafka, APP_NAME, - image_version, + &kafka.product_version(), CONTROLLER_NAME, &rolegroup_ref.role, &rolegroup_ref.role_group, @@ -838,7 +822,7 @@ fn build_broker_rolegroup_statefulset( .with_recommended_labels( kafka, APP_NAME, - image_version, + &kafka.product_version(), CONTROLLER_NAME, &rolegroup_ref.role, &rolegroup_ref.role_group, From 399b11883a2d32b19b44f10c50ab905b829bb062 Mon Sep 17 00:00:00 2001 From: Sebastian Bernauer Date: Thu, 6 Oct 2022 19:56:04 +0200 Subject: [PATCH 03/19] adapt to new resolved product image --- Cargo.lock | 4 +- deploy/crd/kafkacluster.crd.yaml | 19 ++++++ rust/crd/src/lib.rs | 17 +---- rust/operator/src/discovery.rs | 14 +++- rust/operator/src/kafka_controller.rs | 68 +++++++++++++------ .../kuttl/smoke/01-install-kafka.yaml.j2 | 4 +- 6 files changed, 84 insertions(+), 42 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 137212af..06230624 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1709,7 +1709,7 @@ dependencies = [ [[package]] name = "stackable-operator" version = "0.25.1" -source = "git+https://github.com/stackabletech/operator-rs.git?branch=feature/product-image-selection#ce854e828b3b7900fec55661bbb805534349e506" +source = "git+https://github.com/stackabletech/operator-rs.git?branch=feature/product-image-selection#51897a74101a92a258de163439c323c86353e97b" dependencies = [ "chrono", "clap", @@ -1742,7 +1742,7 @@ dependencies = [ [[package]] name = "stackable-operator-derive" version = "0.25.1" -source = "git+https://github.com/stackabletech/operator-rs.git?branch=feature/product-image-selection#ce854e828b3b7900fec55661bbb805534349e506" +source = "git+https://github.com/stackabletech/operator-rs.git?branch=feature/product-image-selection#51897a74101a92a258de163439c323c86353e97b" dependencies = [ "darling", "proc-macro2", diff --git a/deploy/crd/kafkacluster.crd.yaml b/deploy/crd/kafkacluster.crd.yaml index c48e49ca..58da7550 100644 --- a/deploy/crd/kafkacluster.crd.yaml +++ b/deploy/crd/kafkacluster.crd.yaml @@ -579,6 +579,25 @@ spec: productVersion: description: Version of the product, e.g. `1.4.1`. type: string + pullPolicy: + default: IfNotPresent + description: '[Pull policy](https://kubernetes.io/docs/concepts/containers/images/#image-pull-policy) used when pulling the Images' + enum: + - IfNotPresent + - Always + - Never + type: string + pullSecrets: + description: '[Image pull secrets](https://kubernetes.io/docs/concepts/containers/images/#specifying-imagepullsecrets-on-a-pod) to pull images from a private registry' + items: + description: LocalObjectReference contains enough information to let you locate the referenced object inside the same namespace. + properties: + name: + description: 'Name of the referent. More info: https://kubernetes.io/docs/concepts/overview/working-with-objects/names/#names' + type: string + type: object + nullable: true + type: array repo: description: Name of the docker repo, e.g. `docker.stackable.tech/stackable` nullable: true diff --git a/rust/crd/src/lib.rs b/rust/crd/src/lib.rs index b0b57984..bccc697b 100644 --- a/rust/crd/src/lib.rs +++ b/rust/crd/src/lib.rs @@ -2,7 +2,7 @@ pub mod listener; use serde::{Deserialize, Serialize}; use snafu::{OptionExt, Snafu}; -use stackable_operator::commons::product_image_selection::ProductImageSelection; +use stackable_operator::commons::product_image_selection::ProductImage; use stackable_operator::memory::to_java_heap; use stackable_operator::{ commons::{ @@ -115,7 +115,7 @@ pub enum Error { )] #[serde(rename_all = "camelCase")] pub struct KafkaClusterSpec { - pub image: ProductImageSelection, + pub image: ProductImage, pub brokers: Option>, pub zookeeper_config_map_name: String, pub opa: Option, @@ -300,19 +300,6 @@ impl KafkaCluster { .transpose() } - /// Returns the product version, e.g. `2.1.0` - pub fn product_version(&self) -> String { - self.spec - .image - .resolve(DOCKER_IMAGE_BASE_NAME) - .product_version - } - - /// Returns the full image name e.g. `docker.stackable.tech/stackable/superset:1.4.1-stackable2.1.0` - pub fn image(&self) -> String { - self.spec.image.resolve(DOCKER_IMAGE_BASE_NAME).image - } - /// Returns the secret class for client connection encryption. Defaults to `tls`. pub fn client_tls_secret_class(&self) -> Option<&TlsSecretClass> { let spec: &KafkaClusterSpec = &self.spec; diff --git a/rust/operator/src/discovery.rs b/rust/operator/src/discovery.rs index e836223d..1eebed0c 100644 --- a/rust/operator/src/discovery.rs +++ b/rust/operator/src/discovery.rs @@ -4,6 +4,7 @@ use snafu::{OptionExt, ResultExt, Snafu}; use stackable_kafka_crd::{KafkaCluster, KafkaRole, APP_NAME}; use stackable_operator::{ builder::{ConfigMapBuilder, ObjectMetaBuilder}, + commons::product_image_selection::ResolvedProductImage, k8s_openapi::api::core::v1::{ConfigMap, Endpoints, Service, ServicePort}, kube::{runtime::reflector::ObjectRef, Resource, ResourceExt}, }; @@ -46,16 +47,24 @@ pub async fn build_discovery_configmaps( owner: &impl Resource, kafka: &KafkaCluster, svc: &Service, + resolved_product_image: &ResolvedProductImage, ) -> Result, Error> { let name = owner.name_any(); let port_name = kafka.client_port_name(); Ok(vec![ - build_discovery_configmap(&name, owner, kafka, service_hosts(svc, port_name)?)?, + build_discovery_configmap( + &name, + owner, + kafka, + service_hosts(svc, port_name)?, + resolved_product_image, + )?, build_discovery_configmap( &format!("{}-nodeport", name), owner, kafka, nodeport_hosts(client, svc, port_name).await?, + resolved_product_image, )?, ]) } @@ -68,6 +77,7 @@ fn build_discovery_configmap( owner: &impl Resource, kafka: &KafkaCluster, hosts: impl IntoIterator, u16)>, + resolved_product_image: &ResolvedProductImage, ) -> Result { // Write a list of bootstrap servers in the format that Kafka clients: // "{host1}:{port1},{host2:port2},..." @@ -88,7 +98,7 @@ fn build_discovery_configmap( .with_recommended_labels( kafka, APP_NAME, - &kafka.product_version(), + &resolved_product_image.product_version, CONTROLLER_NAME, &KafkaRole::Broker.to_string(), "discovery", diff --git a/rust/operator/src/kafka_controller.rs b/rust/operator/src/kafka_controller.rs index 8813675e..1713e93a 100644 --- a/rust/operator/src/kafka_controller.rs +++ b/rust/operator/src/kafka_controller.rs @@ -3,11 +3,11 @@ use snafu::{OptionExt, ResultExt, Snafu}; use stackable_kafka_crd::{ listener::get_kafka_listener_config, KafkaCluster, KafkaRole, TlsSecretClass, APP_NAME, - CLIENT_PORT, CLIENT_PORT_NAME, KAFKA_HEAP_OPTS, LOG_DIRS_VOLUME_NAME, METRICS_PORT, - METRICS_PORT_NAME, SECURE_CLIENT_PORT, SECURE_CLIENT_PORT_NAME, SERVER_PROPERTIES_FILE, - STACKABLE_CONFIG_DIR, STACKABLE_DATA_DIR, STACKABLE_TLS_CLIENT_AUTH_DIR, - STACKABLE_TLS_CLIENT_DIR, STACKABLE_TLS_INTERNAL_DIR, STACKABLE_TMP_DIR, - TLS_DEFAULT_SECRET_CLASS, + CLIENT_PORT, CLIENT_PORT_NAME, DOCKER_IMAGE_BASE_NAME, KAFKA_HEAP_OPTS, LOG_DIRS_VOLUME_NAME, + METRICS_PORT, METRICS_PORT_NAME, SECURE_CLIENT_PORT, SECURE_CLIENT_PORT_NAME, + SERVER_PROPERTIES_FILE, STACKABLE_CONFIG_DIR, STACKABLE_DATA_DIR, + STACKABLE_TLS_CLIENT_AUTH_DIR, STACKABLE_TLS_CLIENT_DIR, STACKABLE_TLS_INTERNAL_DIR, + STACKABLE_TMP_DIR, TLS_DEFAULT_SECRET_CLASS, }; use stackable_operator::{ builder::{ @@ -17,6 +17,7 @@ use stackable_operator::{ commons::{ authentication::{AuthenticationClass, AuthenticationClassProvider}, opa::OpaApiVersion, + product_image_selection::ResolvedProductImage, tls::TlsAuthenticationProvider, }, k8s_openapi::{ @@ -222,11 +223,13 @@ impl ReconcilerError for Error { } pub async fn reconcile_kafka(kafka: Arc, ctx: Arc) -> Result { + let resolved_product_image = kafka.spec.image.resolve(DOCKER_IMAGE_BASE_NAME); + tracing::info!("Starting reconcile"); let client = &ctx.client; let validated_config = validate_all_roles_and_groups_config( - &kafka.product_version(), + &resolved_product_image.product_version, &transform_all_roles_to_config( &*kafka, [( @@ -285,9 +288,9 @@ pub async fn reconcile_kafka(kafka: Arc, ctx: Arc) -> Result< None }; - let broker_role_service = build_broker_role_service(&kafka)?; + let broker_role_service = build_broker_role_service(&kafka, &resolved_product_image)?; let (broker_role_serviceaccount, broker_role_rolebinding) = - build_broker_role_serviceaccount(&kafka, &ctx.controller_config)?; + build_broker_role_serviceaccount(&kafka, &ctx.controller_config, &resolved_product_image)?; let broker_role_serviceaccount_ref = ObjectRef::from_obj(&broker_role_serviceaccount); let broker_role_service = client .apply_patch(CONTROLLER_NAME, &broker_role_service, &broker_role_service) @@ -313,8 +316,14 @@ pub async fn reconcile_kafka(kafka: Arc, ctx: Arc) -> Result< for (rolegroup_name, rolegroup_config) in role_broker_config.iter() { let rolegroup = kafka.broker_rolegroup_ref(rolegroup_name); - let rg_service = build_broker_rolegroup_service(&rolegroup, &kafka)?; - let rg_configmap = build_broker_rolegroup_config_map(&rolegroup, &kafka, rolegroup_config)?; + let rg_service = + build_broker_rolegroup_service(&rolegroup, &kafka, &resolved_product_image)?; + let rg_configmap = build_broker_rolegroup_config_map( + &rolegroup, + &kafka, + rolegroup_config, + &resolved_product_image, + )?; let rg_statefulset = build_broker_rolegroup_statefulset( &rolegroup, &kafka, @@ -322,6 +331,7 @@ pub async fn reconcile_kafka(kafka: Arc, ctx: Arc) -> Result< &broker_role_serviceaccount_ref, opa_connect.as_deref(), client_authentication_class.as_ref(), + &resolved_product_image, )?; client .apply_patch(CONTROLLER_NAME, &rg_service, &rg_service) @@ -343,9 +353,15 @@ pub async fn reconcile_kafka(kafka: Arc, ctx: Arc) -> Result< })?; } - for discovery_cm in build_discovery_configmaps(client, &*kafka, &kafka, &broker_role_service) - .await - .context(BuildDiscoveryConfigSnafu)? + for discovery_cm in build_discovery_configmaps( + client, + &*kafka, + &kafka, + &broker_role_service, + &resolved_product_image, + ) + .await + .context(BuildDiscoveryConfigSnafu)? { client .apply_patch(CONTROLLER_NAME, &discovery_cm, &discovery_cm) @@ -358,7 +374,10 @@ pub async fn reconcile_kafka(kafka: Arc, ctx: Arc) -> Result< /// The broker-role service is the primary endpoint that should be used by clients that do not perform internal load balancing, /// including targets outside of the cluster. -pub fn build_broker_role_service(kafka: &KafkaCluster) -> Result { +pub fn build_broker_role_service( + kafka: &KafkaCluster, + resolved_product_image: &ResolvedProductImage, +) -> Result { let role_name = KafkaRole::Broker.to_string(); let role_svc_name = kafka .broker_role_service_name() @@ -372,7 +391,7 @@ pub fn build_broker_role_service(kafka: &KafkaCluster) -> Result { .with_recommended_labels( kafka, APP_NAME, - &kafka.product_version(), + &resolved_product_image.product_version, CONTROLLER_NAME, &role_name, "global", @@ -391,6 +410,7 @@ pub fn build_broker_role_service(kafka: &KafkaCluster) -> Result { fn build_broker_role_serviceaccount( kafka: &KafkaCluster, controller_config: &ControllerConfig, + resolved_product_image: &ResolvedProductImage, ) -> Result<(ServiceAccount, RoleBinding)> { let role_name = KafkaRole::Broker.to_string(); let sa_name = format!("{}-{}", kafka.metadata.name.as_ref().unwrap(), role_name); @@ -403,7 +423,7 @@ fn build_broker_role_serviceaccount( .with_recommended_labels( kafka, APP_NAME, - &kafka.product_version(), + &resolved_product_image.product_version, CONTROLLER_NAME, &role_name, "global", @@ -421,7 +441,7 @@ fn build_broker_role_serviceaccount( .with_recommended_labels( kafka, APP_NAME, - &kafka.product_version(), + &resolved_product_image.product_version, CONTROLLER_NAME, &role_name, "global", @@ -447,6 +467,7 @@ fn build_broker_rolegroup_config_map( rolegroup: &RoleGroupRef, kafka: &KafkaCluster, broker_config: &HashMap>, + resolved_product_image: &ResolvedProductImage, ) -> Result { let server_cfg = broker_config .get(&PropertyNameKind::File(SERVER_PROPERTIES_FILE.to_string())) @@ -466,7 +487,7 @@ fn build_broker_rolegroup_config_map( .with_recommended_labels( kafka, APP_NAME, - &kafka.product_version(), + &resolved_product_image.product_version, CONTROLLER_NAME, &rolegroup.role, &rolegroup.role_group, @@ -497,6 +518,7 @@ fn build_broker_rolegroup_config_map( fn build_broker_rolegroup_service( rolegroup: &RoleGroupRef, kafka: &KafkaCluster, + resolved_product_image: &ResolvedProductImage, ) -> Result { Ok(Service { metadata: ObjectMetaBuilder::new() @@ -507,7 +529,7 @@ fn build_broker_rolegroup_service( .with_recommended_labels( kafka, APP_NAME, - &kafka.product_version(), + &resolved_product_image.product_version, CONTROLLER_NAME, &rolegroup.role, &rolegroup.role_group, @@ -540,6 +562,7 @@ fn build_broker_rolegroup_statefulset( serviceaccount: &ObjectRef, opa_connect_string: Option<&str>, client_authentication_class: Option<&AuthenticationClass>, + resolved_product_image: &ResolvedProductImage, ) -> Result { let mut cb_kafka = ContainerBuilder::new(APP_NAME).expect("ContainerBuilder not created"); let mut cb_prepare = ContainerBuilder::new("prepare").expect("ContainerBuilder not created"); @@ -733,7 +756,7 @@ fn build_broker_rolegroup_statefulset( }); cb_kafka - .image(kafka.image()) + .image_from_product_image(resolved_product_image) .args(vec![ "sh".to_string(), "-c".to_string(), @@ -779,13 +802,14 @@ fn build_broker_rolegroup_statefulset( m.with_recommended_labels( kafka, APP_NAME, - &kafka.product_version(), + &resolved_product_image.product_version, CONTROLLER_NAME, &rolegroup_ref.role, &rolegroup_ref.role_group, ) .with_label(pod_svc_controller::LABEL_ENABLE, "true") }) + .image_pull_secrets_from_product_image(resolved_product_image) .add_init_container(cb_prepare.build()) .add_init_container(container_get_svc) .add_container(cb_kafka.build()) @@ -822,7 +846,7 @@ fn build_broker_rolegroup_statefulset( .with_recommended_labels( kafka, APP_NAME, - &kafka.product_version(), + &resolved_product_image.product_version, CONTROLLER_NAME, &rolegroup_ref.role, &rolegroup_ref.role_group, diff --git a/tests/templates/kuttl/smoke/01-install-kafka.yaml.j2 b/tests/templates/kuttl/smoke/01-install-kafka.yaml.j2 index 9e6ef15e..3a047114 100644 --- a/tests/templates/kuttl/smoke/01-install-kafka.yaml.j2 +++ b/tests/templates/kuttl/smoke/01-install-kafka.yaml.j2 @@ -10,7 +10,9 @@ kind: KafkaCluster metadata: name: simple-kafka spec: - version: {{ test_scenario['values']['kafka'] }} + image: + productVersion: {{ test_scenario['values']['kafka'].split('-stackable')[0] }} + stackableVersion: {{ test_scenario['values']['kafka'].split('-stackable')[1] }} zookeeperConfigMapName: kafka-zk config: {% if test_scenario['values']['use-client-tls'] == 'true' %} From 92d79e75d03f76c207e99d0ae78ef3b7fccd4b55 Mon Sep 17 00:00:00 2001 From: Sebastian Bernauer Date: Thu, 6 Oct 2022 19:57:38 +0200 Subject: [PATCH 04/19] update --- deploy/helm/kafka-operator/crds/crds.yaml | 48 +++++++++++++++++++++-- deploy/manifests/crds.yaml | 48 +++++++++++++++++++++-- 2 files changed, 90 insertions(+), 6 deletions(-) diff --git a/deploy/helm/kafka-operator/crds/crds.yaml b/deploy/helm/kafka-operator/crds/crds.yaml index 4fd32a5b..bf4e6ca3 100644 --- a/deploy/helm/kafka-operator/crds/crds.yaml +++ b/deploy/helm/kafka-operator/crds/crds.yaml @@ -564,6 +564,50 @@ spec: - secretClass type: object type: object + image: + anyOf: + - required: + - custom + - productVersion + - required: + - productVersion + - stackableVersion + - required: + - productVersion + properties: + custom: + description: Overwrite the docker image. Specify the full docker image name, e.g. `docker.stackable.tech/stackable/superset:1.4.1-stackable2.1.0` + type: string + productVersion: + description: Version of the product, e.g. `1.4.1`. + type: string + pullPolicy: + default: IfNotPresent + description: '[Pull policy](https://kubernetes.io/docs/concepts/containers/images/#image-pull-policy) used when pulling the Images' + enum: + - IfNotPresent + - Always + - Never + type: string + pullSecrets: + description: '[Image pull secrets](https://kubernetes.io/docs/concepts/containers/images/#specifying-imagepullsecrets-on-a-pod) to pull images from a private registry' + items: + description: LocalObjectReference contains enough information to let you locate the referenced object inside the same namespace. + properties: + name: + description: 'Name of the referent. More info: https://kubernetes.io/docs/concepts/overview/working-with-objects/names/#names' + type: string + type: object + nullable: true + type: array + repo: + description: Name of the docker repo, e.g. `docker.stackable.tech/stackable` + nullable: true + type: string + stackableVersion: + description: Stackable version of the product, e.g. 2.1.0 + type: string + type: object log4j: nullable: true type: string @@ -581,12 +625,10 @@ spec: stopped: nullable: true type: boolean - version: - nullable: true - type: string zookeeperConfigMapName: type: string required: + - image - zookeeperConfigMapName type: object required: diff --git a/deploy/manifests/crds.yaml b/deploy/manifests/crds.yaml index e69a047e..71cd6be2 100644 --- a/deploy/manifests/crds.yaml +++ b/deploy/manifests/crds.yaml @@ -565,6 +565,50 @@ spec: - secretClass type: object type: object + image: + anyOf: + - required: + - custom + - productVersion + - required: + - productVersion + - stackableVersion + - required: + - productVersion + properties: + custom: + description: Overwrite the docker image. Specify the full docker image name, e.g. `docker.stackable.tech/stackable/superset:1.4.1-stackable2.1.0` + type: string + productVersion: + description: Version of the product, e.g. `1.4.1`. + type: string + pullPolicy: + default: IfNotPresent + description: '[Pull policy](https://kubernetes.io/docs/concepts/containers/images/#image-pull-policy) used when pulling the Images' + enum: + - IfNotPresent + - Always + - Never + type: string + pullSecrets: + description: '[Image pull secrets](https://kubernetes.io/docs/concepts/containers/images/#specifying-imagepullsecrets-on-a-pod) to pull images from a private registry' + items: + description: LocalObjectReference contains enough information to let you locate the referenced object inside the same namespace. + properties: + name: + description: 'Name of the referent. More info: https://kubernetes.io/docs/concepts/overview/working-with-objects/names/#names' + type: string + type: object + nullable: true + type: array + repo: + description: Name of the docker repo, e.g. `docker.stackable.tech/stackable` + nullable: true + type: string + stackableVersion: + description: Stackable version of the product, e.g. 2.1.0 + type: string + type: object log4j: nullable: true type: string @@ -582,12 +626,10 @@ spec: stopped: nullable: true type: boolean - version: - nullable: true - type: string zookeeperConfigMapName: type: string required: + - image - zookeeperConfigMapName type: object required: From af5372290d1ac1d59e1f14a6f6b0db519f7e0896 Mon Sep 17 00:00:00 2001 From: Sebastian Bernauer Date: Fri, 28 Oct 2022 11:26:55 +0200 Subject: [PATCH 05/19] lint --- rust/crd/src/lib.rs | 7 ++++--- rust/operator/src/kafka_controller.rs | 21 +++++++++++++-------- 2 files changed, 17 insertions(+), 11 deletions(-) diff --git a/rust/crd/src/lib.rs b/rust/crd/src/lib.rs index 1b3029ed..f403c620 100644 --- a/rust/crd/src/lib.rs +++ b/rust/crd/src/lib.rs @@ -5,9 +5,10 @@ use snafu::{OptionExt, Snafu}; use stackable_operator::commons::{ product_image_selection::ProductImage, resources::{ - CpuLimitsFragment, MemoryLimitsFragment, NoRuntimeLimitsFragment, PvcConfigFragment, - ResourcesFragment, -}}; + CpuLimitsFragment, MemoryLimitsFragment, NoRuntimeLimitsFragment, PvcConfigFragment, + ResourcesFragment, + }, +}; use stackable_operator::config::fragment::{Fragment, ValidationError}; use stackable_operator::memory::to_java_heap; use stackable_operator::role_utils::RoleGroup; diff --git a/rust/operator/src/kafka_controller.rs b/rust/operator/src/kafka_controller.rs index adcbde55..0f03453c 100644 --- a/rust/operator/src/kafka_controller.rs +++ b/rust/operator/src/kafka_controller.rs @@ -3,11 +3,11 @@ use snafu::{OptionExt, ResultExt, Snafu}; use stackable_kafka_crd::{ listener::get_kafka_listener_config, KafkaCluster, KafkaConfig, KafkaRole, TlsSecretClass, - APP_NAME, CLIENT_PORT, CLIENT_PORT_NAME, KAFKA_HEAP_OPTS, LOG_DIRS_VOLUME_NAME, METRICS_PORT, - METRICS_PORT_NAME, SECURE_CLIENT_PORT, SECURE_CLIENT_PORT_NAME, SERVER_PROPERTIES_FILE, - STACKABLE_CONFIG_DIR, STACKABLE_DATA_DIR, STACKABLE_TLS_CLIENT_AUTH_DIR, - STACKABLE_TLS_CLIENT_DIR, STACKABLE_TLS_INTERNAL_DIR, STACKABLE_TMP_DIR, - TLS_DEFAULT_SECRET_CLASS, DOCKER_IMAGE_BASE_NAME, + APP_NAME, CLIENT_PORT, CLIENT_PORT_NAME, DOCKER_IMAGE_BASE_NAME, KAFKA_HEAP_OPTS, + LOG_DIRS_VOLUME_NAME, METRICS_PORT, METRICS_PORT_NAME, SECURE_CLIENT_PORT, + SECURE_CLIENT_PORT_NAME, SERVER_PROPERTIES_FILE, STACKABLE_CONFIG_DIR, STACKABLE_DATA_DIR, + STACKABLE_TLS_CLIENT_AUTH_DIR, STACKABLE_TLS_CLIENT_DIR, STACKABLE_TLS_INTERNAL_DIR, + STACKABLE_TMP_DIR, TLS_DEFAULT_SECRET_CLASS, }; use stackable_operator::{ builder::{ @@ -340,9 +340,14 @@ pub async fn reconcile_kafka(kafka: Arc, ctx: Arc) -> Result< rolegroup: rolegroup_ref.clone(), })?; - let rg_service = build_broker_rolegroup_service(&rolegroup_ref, &kafka, &resolved_product_image)?; - let rg_configmap = - build_broker_rolegroup_config_map(&rolegroup_ref, &kafka, rolegroup_config, &resolved_product_image)?; + let rg_service = + build_broker_rolegroup_service(&rolegroup_ref, &kafka, &resolved_product_image)?; + let rg_configmap = build_broker_rolegroup_config_map( + &rolegroup_ref, + &kafka, + rolegroup_config, + &resolved_product_image, + )?; let rg_statefulset = build_broker_rolegroup_statefulset( &rolegroup_ref, &kafka, From 3761c63657d56a83275740f53b0ca58d2e331db9 Mon Sep 17 00:00:00 2001 From: Sebastian Bernauer Date: Fri, 28 Oct 2022 11:47:24 +0200 Subject: [PATCH 06/19] fix tests --- rust/crd/src/lib.rs | 28 +++++++++++++++++++++------- rust/crd/src/listener.rs | 12 +++++++++--- 2 files changed, 30 insertions(+), 10 deletions(-) diff --git a/rust/crd/src/lib.rs b/rust/crd/src/lib.rs index f403c620..2392527f 100644 --- a/rust/crd/src/lib.rs +++ b/rust/crd/src/lib.rs @@ -563,7 +563,9 @@ mod tests { metadata: name: simple-kafka spec: - version: abc + image: + productVersion: 42.0.0 + stackableVersion: 0.42.0 zookeeperConfigMapName: xyz "#; let kafka: KafkaCluster = serde_yaml::from_str(input).expect("illegal test input"); @@ -582,7 +584,9 @@ mod tests { metadata: name: simple-kafka spec: - version: abc + image: + productVersion: 42.0.0 + stackableVersion: 0.42.0 zookeeperConfigMapName: xyz config: tls: @@ -604,7 +608,9 @@ mod tests { metadata: name: simple-kafka spec: - version: abc + image: + productVersion: 42.0.0 + stackableVersion: 0.42.0 zookeeperConfigMapName: xyz config: tls: null @@ -622,7 +628,9 @@ mod tests { metadata: name: simple-kafka spec: - version: abc + image: + productVersion: 42.0.0 + stackableVersion: 0.42.0 zookeeperConfigMapName: xyz config: internalTls: @@ -647,7 +655,9 @@ mod tests { metadata: name: simple-kafka spec: - version: abc + image: + productVersion: 42.0.0 + stackableVersion: 0.42.0 zookeeperConfigMapName: xyz "#; let kafka: KafkaCluster = serde_yaml::from_str(input).expect("illegal test input"); @@ -666,7 +676,9 @@ mod tests { metadata: name: simple-kafka spec: - version: abc + image: + productVersion: 42.0.0 + stackableVersion: 0.42.0 zookeeperConfigMapName: xyz config: internalTls: @@ -688,7 +700,9 @@ mod tests { metadata: name: simple-kafka spec: - version: abc + image: + productVersion: 42.0.0 + stackableVersion: 0.42.0 zookeeperConfigMapName: xyz config: tls: diff --git a/rust/crd/src/listener.rs b/rust/crd/src/listener.rs index abb00fd8..d1d2be8e 100644 --- a/rust/crd/src/listener.rs +++ b/rust/crd/src/listener.rs @@ -207,7 +207,9 @@ mod tests { name: simple-kafka namespace: default spec: - version: abc + image: + productVersion: 42.0.0 + stackableVersion: 0.42.0 zookeeperConfigMapName: xyz config: tls: @@ -264,7 +266,9 @@ mod tests { name: simple-kafka namespace: default spec: - version: abc + image: + productVersion: 42.0.0 + stackableVersion: 0.42.0 zookeeperConfigMapName: xyz config: tls: @@ -317,7 +321,9 @@ mod tests { name: simple-kafka namespace: default spec: - version: abc + image: + productVersion: 42.0.0 + stackableVersion: 0.42.0 zookeeperConfigMapName: xyz config: tls: null From 607a0023b5b574d4ba246b4c34f23f98a736de96 Mon Sep 17 00:00:00 2001 From: Sebastian Bernauer Date: Fri, 28 Oct 2022 13:55:11 +0200 Subject: [PATCH 07/19] Update tests --- tests/templates/kuttl/configuration/01-install-kafka.yaml.j2 | 4 +++- .../kuttl/delete-rolegroup/01-install-kafka.yaml.j2 | 4 +++- .../kuttl/delete-rolegroup/02-delete-secondary.yaml.j2 | 5 +++-- tests/templates/kuttl/smoke/01-install-kafka.yaml.j2 | 4 ++-- tests/templates/kuttl/tls/20-install-kafka.yaml.j2 | 4 +++- tests/templates/kuttl/upgrade/01-install-kafka.yaml.j2 | 4 +++- tests/templates/kuttl/upgrade/03-upgrade-kafka.yaml.j2 | 2 +- 7 files changed, 18 insertions(+), 9 deletions(-) diff --git a/tests/templates/kuttl/configuration/01-install-kafka.yaml.j2 b/tests/templates/kuttl/configuration/01-install-kafka.yaml.j2 index 3942aca7..4757104d 100644 --- a/tests/templates/kuttl/configuration/01-install-kafka.yaml.j2 +++ b/tests/templates/kuttl/configuration/01-install-kafka.yaml.j2 @@ -10,7 +10,9 @@ kind: KafkaCluster metadata: name: simple-kafka spec: - version: {{ test_scenario['values']['kafka-latest'] }} + image: + productVersion: "{{ test_scenario['values']['kafka-latest'].split('-stackable')[0] }}" + stackableVersion: "{{ test_scenario['values']['kafka-latest'].split('-stackable')[1] }}" zookeeperConfigMapName: kafka-zk brokers: config: diff --git a/tests/templates/kuttl/delete-rolegroup/01-install-kafka.yaml.j2 b/tests/templates/kuttl/delete-rolegroup/01-install-kafka.yaml.j2 index 33c243c4..b2e38708 100644 --- a/tests/templates/kuttl/delete-rolegroup/01-install-kafka.yaml.j2 +++ b/tests/templates/kuttl/delete-rolegroup/01-install-kafka.yaml.j2 @@ -10,7 +10,9 @@ kind: KafkaCluster metadata: name: simple-kafka spec: - version: {{ test_scenario['values']['kafka'] }} + image: + productVersion: "{{ test_scenario['values']['kafka'].split('-stackable')[0] }}" + stackableVersion: "{{ test_scenario['values']['kafka'].split('-stackable')[1] }}" zookeeperConfigMapName: kafka-zk brokers: roleGroups: diff --git a/tests/templates/kuttl/delete-rolegroup/02-delete-secondary.yaml.j2 b/tests/templates/kuttl/delete-rolegroup/02-delete-secondary.yaml.j2 index 091cf3ff..af04c30f 100644 --- a/tests/templates/kuttl/delete-rolegroup/02-delete-secondary.yaml.j2 +++ b/tests/templates/kuttl/delete-rolegroup/02-delete-secondary.yaml.j2 @@ -10,9 +10,10 @@ kind: KafkaCluster metadata: name: simple-kafka spec: - version: {{ test_scenario['values']['kafka'] }} + image: + productVersion: "{{ test_scenario['values']['kafka'].split('-stackable')[0] }}" + stackableVersion: "{{ test_scenario['values']['kafka'].split('-stackable')[1] }}" zookeeperConfigMapName: kafka-zk - config: brokers: roleGroups: default: diff --git a/tests/templates/kuttl/smoke/01-install-kafka.yaml.j2 b/tests/templates/kuttl/smoke/01-install-kafka.yaml.j2 index 3a047114..b988fa23 100644 --- a/tests/templates/kuttl/smoke/01-install-kafka.yaml.j2 +++ b/tests/templates/kuttl/smoke/01-install-kafka.yaml.j2 @@ -11,8 +11,8 @@ metadata: name: simple-kafka spec: image: - productVersion: {{ test_scenario['values']['kafka'].split('-stackable')[0] }} - stackableVersion: {{ test_scenario['values']['kafka'].split('-stackable')[1] }} + productVersion: "{{ test_scenario['values']['kafka'].split('-stackable')[0] }}" + stackableVersion: "{{ test_scenario['values']['kafka'].split('-stackable')[1] }}" zookeeperConfigMapName: kafka-zk config: {% if test_scenario['values']['use-client-tls'] == 'true' %} diff --git a/tests/templates/kuttl/tls/20-install-kafka.yaml.j2 b/tests/templates/kuttl/tls/20-install-kafka.yaml.j2 index 6952f3f7..79c2de68 100644 --- a/tests/templates/kuttl/tls/20-install-kafka.yaml.j2 +++ b/tests/templates/kuttl/tls/20-install-kafka.yaml.j2 @@ -51,7 +51,9 @@ kind: KafkaCluster metadata: name: test-kafka spec: - version: {{ test_scenario['values']['kafka'] }} + image: + productVersion: "{{ test_scenario['values']['kafka'].split('-stackable')[0] }}" + stackableVersion: "{{ test_scenario['values']['kafka'].split('-stackable')[1] }}" zookeeperConfigMapName: test-kafka-znode config: {% if test_scenario['values']['use-client-tls'] == 'true' %} diff --git a/tests/templates/kuttl/upgrade/01-install-kafka.yaml.j2 b/tests/templates/kuttl/upgrade/01-install-kafka.yaml.j2 index 393de25d..b86e588d 100644 --- a/tests/templates/kuttl/upgrade/01-install-kafka.yaml.j2 +++ b/tests/templates/kuttl/upgrade/01-install-kafka.yaml.j2 @@ -32,7 +32,9 @@ kind: KafkaCluster metadata: name: simple-kafka spec: - version: {{ test_scenario['values']['upgrade_old'] }} + image: + productVersion: "{{ test_scenario['values']['upgrade_old'].split('-stackable')[0] }}" + stackableVersion: "{{ test_scenario['values']['upgrade_old'].split('-stackable')[1] }}" zookeeperConfigMapName: kafka-zk config: {% if test_scenario['values']['use-client-tls'] == 'true' %} diff --git a/tests/templates/kuttl/upgrade/03-upgrade-kafka.yaml.j2 b/tests/templates/kuttl/upgrade/03-upgrade-kafka.yaml.j2 index 8e81a2fd..c2e237ca 100644 --- a/tests/templates/kuttl/upgrade/03-upgrade-kafka.yaml.j2 +++ b/tests/templates/kuttl/upgrade/03-upgrade-kafka.yaml.j2 @@ -6,4 +6,4 @@ commands: - script: >- kubectl --namespace $NAMESPACE patch kafkaclusters.kafka.stackable.tech simple-kafka - --type=merge --patch '{ "spec": { "version": "{{ test_scenario['values']['upgrade_new'] }}" }}' + --type=merge --patch '{ "spec": { "image": { "productVersion": "{{ test_scenario['values']['upgrade_new'].split('-stackable')[0] }}", "stackableVersion": "{{ test_scenario['values']['upgrade_new'].split('-stackable')[1] }}" }}}' From 256c70d4090f1c072fdd0da0961bf2428e7d7696 Mon Sep 17 00:00:00 2001 From: Sebastian Bernauer Date: Wed, 2 Nov 2022 08:03:59 +0100 Subject: [PATCH 08/19] Remove Error::KafkaVersionParseFailure --- rust/operator/src/discovery.rs | 2 -- rust/operator/src/kafka_controller.rs | 3 --- 2 files changed, 5 deletions(-) diff --git a/rust/operator/src/discovery.rs b/rust/operator/src/discovery.rs index 4eb2a98a..53843ce0 100644 --- a/rust/operator/src/discovery.rs +++ b/rust/operator/src/discovery.rs @@ -35,8 +35,6 @@ pub enum Error { BuildConfigMap { source: stackable_operator::error::Error, }, - #[snafu(display("failed to parse Kafka version/image"))] - KafkaVersionParseFailure { source: stackable_kafka_crd::Error }, } /// Builds discovery [`ConfigMap`]s for connecting to a [`KafkaCluster`] for all expected scenarios diff --git a/rust/operator/src/kafka_controller.rs b/rust/operator/src/kafka_controller.rs index 0f03453c..028177c9 100644 --- a/rust/operator/src/kafka_controller.rs +++ b/rust/operator/src/kafka_controller.rs @@ -163,8 +163,6 @@ pub enum Error { InvalidJavaHeapConfig { source: stackable_operator::error::Error, }, - #[snafu(display("failed to parse Kafka version/image"))] - KafkaVersionParseFailure { source: stackable_kafka_crd::Error }, #[snafu(display("failed to retrieve {}", authentication_class))] AuthenticationClassRetrieval { source: stackable_operator::error::Error, @@ -226,7 +224,6 @@ impl ReconcilerError for Error { Error::InvalidServiceAccount { .. } => None, Error::InvalidOpaConfig { .. } => None, Error::InvalidJavaHeapConfig { .. } => None, - Error::KafkaVersionParseFailure { .. } => None, Error::AuthenticationClassRetrieval { authentication_class, .. From dc37325385fa46f2aa90b0d541cff2966312b34e Mon Sep 17 00:00:00 2001 From: Sebastian Bernauer Date: Wed, 2 Nov 2022 08:19:18 +0100 Subject: [PATCH 09/19] Move resolving product image down after log statement --- rust/operator/src/kafka_controller.rs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/rust/operator/src/kafka_controller.rs b/rust/operator/src/kafka_controller.rs index 028177c9..9a0233ef 100644 --- a/rust/operator/src/kafka_controller.rs +++ b/rust/operator/src/kafka_controller.rs @@ -240,11 +240,11 @@ impl ReconcilerError for Error { } pub async fn reconcile_kafka(kafka: Arc, ctx: Arc) -> Result { - let resolved_product_image = kafka.spec.image.resolve(DOCKER_IMAGE_BASE_NAME); - tracing::info!("Starting reconcile"); let client = &ctx.client; + let resolved_product_image = kafka.spec.image.resolve(DOCKER_IMAGE_BASE_NAME); + let mut cluster_resources = ClusterResources::new(APP_NAME, RESOURCE_SCOPE, &kafka.object_ref(&())).unwrap(); From c9a015fb655d0f0de23f8600a1ce6bb6cce66f91 Mon Sep 17 00:00:00 2001 From: Sebastian Bernauer Date: Fri, 4 Nov 2022 14:09:14 +0100 Subject: [PATCH 10/19] refresh lock --- Cargo.lock | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index c4eb612f..c05dcf0e 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1701,7 +1701,7 @@ dependencies = [ [[package]] name = "stackable-operator" version = "0.25.3" -source = "git+https://github.com/stackabletech/operator-rs.git?branch=feature/product-image-selection#f6a38f0c1767a86e9c4cb80c5ad44975a178c671" +source = "git+https://github.com/stackabletech/operator-rs.git?branch=feature/product-image-selection#b1d906bbd09801e878963d5f8cf747dcd23cd59e" dependencies = [ "chrono", "clap", @@ -1735,7 +1735,7 @@ dependencies = [ [[package]] name = "stackable-operator-derive" version = "0.25.3" -source = "git+https://github.com/stackabletech/operator-rs.git?branch=feature/product-image-selection#f6a38f0c1767a86e9c4cb80c5ad44975a178c671" +source = "git+https://github.com/stackabletech/operator-rs.git?branch=feature/product-image-selection#b1d906bbd09801e878963d5f8cf747dcd23cd59e" dependencies = [ "darling", "proc-macro2", From dd8f7b74bf6c7d2166dde952950c00cb21281996 Mon Sep 17 00:00:00 2001 From: Sebastian Bernauer Date: Mon, 7 Nov 2022 12:56:21 +0100 Subject: [PATCH 11/19] Update examples --- examples/logging/simple-kafka-cluster-opa-log4j.yaml | 4 +++- examples/opa/simple-kafka-cluster-opa-allow-all.yaml | 4 +++- examples/tls/simple-kafka-cluster-tls.yaml | 4 +++- 3 files changed, 9 insertions(+), 3 deletions(-) diff --git a/examples/logging/simple-kafka-cluster-opa-log4j.yaml b/examples/logging/simple-kafka-cluster-opa-log4j.yaml index 56305d14..79db5713 100644 --- a/examples/logging/simple-kafka-cluster-opa-log4j.yaml +++ b/examples/logging/simple-kafka-cluster-opa-log4j.yaml @@ -53,7 +53,9 @@ kind: KafkaCluster metadata: name: simple-kafka spec: - version: 3.2.0-stackable0.1.0 + image: + productVersion: 3.3.1 + stackableVersion: 0.1.0 zookeeperConfigMapName: simple-kafka-znode opa: configMapName: simple-opa diff --git a/examples/opa/simple-kafka-cluster-opa-allow-all.yaml b/examples/opa/simple-kafka-cluster-opa-allow-all.yaml index b6355177..0371da0e 100644 --- a/examples/opa/simple-kafka-cluster-opa-allow-all.yaml +++ b/examples/opa/simple-kafka-cluster-opa-allow-all.yaml @@ -53,7 +53,9 @@ kind: KafkaCluster metadata: name: simple-kafka spec: - version: 3.3.1-stackable0.1.0 + image: + productVersion: 3.3.1 + stackableVersion: 0.1.0 zookeeperConfigMapName: simple-kafka-znode opa: configMapName: simple-opa diff --git a/examples/tls/simple-kafka-cluster-tls.yaml b/examples/tls/simple-kafka-cluster-tls.yaml index 476d365b..82b9b908 100644 --- a/examples/tls/simple-kafka-cluster-tls.yaml +++ b/examples/tls/simple-kafka-cluster-tls.yaml @@ -62,7 +62,9 @@ kind: KafkaCluster metadata: name: simple-kafka spec: - version: 3.3.1-stackable0.1.0 + image: + productVersion: 3.3.1 + stackableVersion: 0.1.0 zookeeperConfigMapName: simple-kafka-znode config: tls: From 8948ad669233e0a7b33e8df7e6dec333d07c2bc2 Mon Sep 17 00:00:00 2001 From: Malte Sander Date: Tue, 13 Dec 2022 11:50:18 +0100 Subject: [PATCH 12/19] resolved conflicts --- rust/operator/src/discovery.rs | 31 +++++-------- rust/operator/src/kafka_controller.rs | 67 ++++++--------------------- 2 files changed, 27 insertions(+), 71 deletions(-) diff --git a/rust/operator/src/discovery.rs b/rust/operator/src/discovery.rs index b29b9f95..c2d27132 100644 --- a/rust/operator/src/discovery.rs +++ b/rust/operator/src/discovery.rs @@ -1,13 +1,15 @@ use crate::utils::build_recommended_labels; use crate::KAFKA_CONTROLLER_NAME; + use snafu::{OptionExt, ResultExt, Snafu}; -use stackable_kafka_crd::{KafkaCluster, KafkaRole, APP_NAME}; +use stackable_kafka_crd::{KafkaCluster, KafkaRole}; use stackable_operator::{ builder::{ConfigMapBuilder, ObjectMetaBuilder}, commons::product_image_selection::ResolvedProductImage, k8s_openapi::api::core::v1::{ConfigMap, Endpoints, Service, ServicePort}, kube::{runtime::reflector::ObjectRef, Resource, ResourceExt}, }; +use std::{collections::BTreeSet, num::TryFromIntError}; #[derive(Snafu, Debug)] pub enum Error { @@ -41,29 +43,26 @@ pub enum Error { pub async fn build_discovery_configmaps( kafka: &KafkaCluster, owner: &impl Resource, + resolved_product_image: &ResolvedProductImage, client: &stackable_operator::client::Client, svc: &Service, - resolved_product_image: &ResolvedProductImage, - app_managed_by: &str, ) -> Result, Error> { let name = owner.name_unchecked(); let port_name = kafka.client_port_name(); Ok(vec![ build_discovery_configmap( - &name, - owner, kafka, - service_hosts(svc, port_name)?, + owner, resolved_product_image, - app_managed_by, + &name, + service_hosts(svc, port_name)?, )?, build_discovery_configmap( - &format!("{}-nodeport", name), - owner, kafka, - nodeport_hosts(client, svc, port_name).await?, + owner, resolved_product_image, - app_managed_by, + &format!("{}-nodeport", name), + nodeport_hosts(client, svc, port_name).await?, )?, ]) } @@ -74,10 +73,9 @@ pub async fn build_discovery_configmaps( fn build_discovery_configmap( kafka: &KafkaCluster, owner: &impl Resource, + resolved_product_image: &ResolvedProductImage, name: &str, hosts: impl IntoIterator, u16)>, - resolved_product_image: &ResolvedProductImage, - app_managed_by: &str, ) -> Result { // Write a list of bootstrap servers in the format that Kafka clients: // "{host1}:{port1},{host2:port2},..." @@ -97,13 +95,8 @@ fn build_discovery_configmap( })? .with_recommended_labels(build_recommended_labels( kafka, - APP_NAME, - &resolved_product_image.product_version, - app_managed_by, KAFKA_CONTROLLER_NAME, - kafka - .image_version() - .context(KafkaVersionParseFailureSnafu)?, + &resolved_product_image.product_version, &KafkaRole::Broker.to_string(), "discovery", )) diff --git a/rust/operator/src/kafka_controller.rs b/rust/operator/src/kafka_controller.rs index 3089dab7..c3e8c5bd 100644 --- a/rust/operator/src/kafka_controller.rs +++ b/rust/operator/src/kafka_controller.rs @@ -80,8 +80,6 @@ pub enum Error { ObjectHasNoName, #[snafu(display("object has no namespace"))] ObjectHasNoNamespace, - #[snafu(display("object defines no version"))] - ObjectHasNoVersion, #[snafu(display("object defines no broker role"))] NoBrokerRole, #[snafu(display("failed to calculate global service name"))] @@ -202,7 +200,6 @@ impl ReconcilerError for Error { match self { Error::ObjectHasNoName => None, Error::ObjectHasNoNamespace => None, - Error::ObjectHasNoVersion => None, Error::NoBrokerRole => None, Error::GlobalServiceNameNotFound => None, Error::ApplyRoleService { .. } => None, @@ -244,8 +241,6 @@ pub async fn reconcile_kafka(kafka: Arc, ctx: Arc) -> Result< let resolved_product_image = kafka.spec.image.resolve(DOCKER_IMAGE_BASE_NAME); - let mut cluster_resources = - ClusterResources::new(APP_NAME, RESOURCE_SCOPE, &kafka.object_ref(&())).unwrap(); let mut cluster_resources = ClusterResources::new( APP_NAME, OPERATOR_NAME, @@ -314,7 +309,7 @@ pub async fn reconcile_kafka(kafka: Arc, ctx: Arc) -> Result< let broker_role_service = build_broker_role_service(&kafka, &resolved_product_image)?; let (broker_role_serviceaccount, broker_role_rolebinding) = - build_broker_role_serviceaccount(&kafka, &ctx.controller_config, &resolved_product_image)?; + build_broker_role_serviceaccount(&kafka, &resolved_product_image, &ctx.controller_config)?; let broker_role_serviceaccount_ref = ObjectRef::from_obj(&broker_role_serviceaccount); let broker_role_service = cluster_resources .add(client, &broker_role_service) @@ -344,22 +339,22 @@ pub async fn reconcile_kafka(kafka: Arc, ctx: Arc) -> Result< })?; let rg_service = - build_broker_rolegroup_service(&rolegroup_ref, &kafka, &resolved_product_image)?; + build_broker_rolegroup_service(&kafka, &resolved_product_image, &rolegroup_ref)?; let rg_configmap = build_broker_rolegroup_config_map( - &rolegroup_ref, &kafka, - rolegroup_config, &resolved_product_image, + &rolegroup_ref, + rolegroup_config, )?; let rg_statefulset = build_broker_rolegroup_statefulset( - &rolegroup_ref, &kafka, + &resolved_product_image, + &rolegroup_ref, rolegroup_config, &broker_role_serviceaccount_ref, opa_connect.as_deref(), client_authentication_class.as_ref(), &rolegroup_typed_config, - &resolved_product_image, )?; cluster_resources .add(client, &rg_service) @@ -382,12 +377,11 @@ pub async fn reconcile_kafka(kafka: Arc, ctx: Arc) -> Result< } for discovery_cm in build_discovery_configmaps( - client, - &*kafka, &kafka, - &broker_role_service, + &*kafka, &resolved_product_image, - RESOURCE_SCOPE, + client, + &broker_role_service, ) .await .context(BuildDiscoveryConfigSnafu)? @@ -425,12 +419,7 @@ pub fn build_broker_role_service( .with_recommended_labels(build_recommended_labels( kafka, KAFKA_CONTROLLER_NAME, - kafka - .image_version() - .context(KafkaVersionParseFailureSnafu)?, - APP_NAME, &resolved_product_image.product_version, - RESOURCE_SCOPE, &role_name, "global", )) @@ -447,8 +436,8 @@ pub fn build_broker_role_service( fn build_broker_role_serviceaccount( kafka: &KafkaCluster, - controller_config: &ControllerConfig, resolved_product_image: &ResolvedProductImage, + controller_config: &ControllerConfig, ) -> Result<(ServiceAccount, RoleBinding)> { let role_name = KafkaRole::Broker.to_string(); let sa_name = format!("{}-{}", kafka.metadata.name.as_ref().unwrap(), role_name); @@ -461,12 +450,7 @@ fn build_broker_role_serviceaccount( .with_recommended_labels(build_recommended_labels( kafka, KAFKA_CONTROLLER_NAME, - kafka - .image_version() - .context(KafkaVersionParseFailureSnafu)?, - APP_NAME, &resolved_product_image.product_version, - RESOURCE_SCOPE, &role_name, "global", )) @@ -483,12 +467,7 @@ fn build_broker_role_serviceaccount( .with_recommended_labels(build_recommended_labels( kafka, KAFKA_CONTROLLER_NAME, - kafka - .image_version() - .context(KafkaVersionParseFailureSnafu)?, - APP_NAME, &resolved_product_image.product_version, - RESOURCE_SCOPE, &role_name, "global", )) @@ -510,10 +489,10 @@ fn build_broker_role_serviceaccount( /// The rolegroup [`ConfigMap`] configures the rolegroup based on the configuration given by the administrator fn build_broker_rolegroup_config_map( - rolegroup: &RoleGroupRef, kafka: &KafkaCluster, - broker_config: &HashMap>, resolved_product_image: &ResolvedProductImage, + rolegroup: &RoleGroupRef, + broker_config: &HashMap>, ) -> Result { let server_cfg = broker_config .get(&PropertyNameKind::File(SERVER_PROPERTIES_FILE.to_string())) @@ -533,12 +512,7 @@ fn build_broker_rolegroup_config_map( .with_recommended_labels(build_recommended_labels( kafka, KAFKA_CONTROLLER_NAME, - kafka - .image_version() - .context(KafkaVersionParseFailureSnafu)?, - APP_NAME, &resolved_product_image.product_version, - RESOURCE_SCOPE, &rolegroup.role, "global", )) @@ -566,9 +540,9 @@ fn build_broker_rolegroup_config_map( /// /// This is mostly useful for internal communication between peers, or for clients that perform client-side load balancing. fn build_broker_rolegroup_service( - rolegroup: &RoleGroupRef, kafka: &KafkaCluster, resolved_product_image: &ResolvedProductImage, + rolegroup: &RoleGroupRef, ) -> Result { Ok(Service { metadata: ObjectMetaBuilder::new() @@ -579,12 +553,7 @@ fn build_broker_rolegroup_service( .with_recommended_labels(build_recommended_labels( kafka, KAFKA_CONTROLLER_NAME, - kafka - .image_version() - .context(KafkaVersionParseFailureSnafu)?, - APP_NAME, &resolved_product_image.product_version, - RESOURCE_SCOPE, &rolegroup.role, &rolegroup.role_group, )) @@ -611,14 +580,14 @@ fn build_broker_rolegroup_service( /// The [`Pod`](`stackable_operator::k8s_openapi::api::core::v1::Pod`)s are accessible through the corresponding [`Service`] (from [`build_broker_rolegroup_service`]). #[allow(clippy::too_many_arguments)] fn build_broker_rolegroup_statefulset( - rolegroup_ref: &RoleGroupRef, kafka: &KafkaCluster, + resolved_product_image: &ResolvedProductImage, + rolegroup_ref: &RoleGroupRef, broker_config: &HashMap>, serviceaccount: &ObjectRef, opa_connect_string: Option<&str>, client_authentication_class: Option<&AuthenticationClass>, rolegroup_typed_config: &KafkaConfig, - resolved_product_image: &ResolvedProductImage, ) -> Result { let mut cb_kafka = ContainerBuilder::new(APP_NAME).context(InvalidContainerNameSnafu { name: APP_NAME })?; @@ -866,10 +835,7 @@ fn build_broker_rolegroup_statefulset( m.with_recommended_labels(build_recommended_labels( kafka, KAFKA_CONTROLLER_NAME, - image_version, - APP_NAME, &resolved_product_image.product_version, - RESOURCE_SCOPE, &rolegroup_ref.role, &rolegroup_ref.role_group, )) @@ -918,10 +884,7 @@ fn build_broker_rolegroup_statefulset( .with_recommended_labels(build_recommended_labels( kafka, KAFKA_CONTROLLER_NAME, - image_version, - APP_NAME, &resolved_product_image.product_version, - RESOURCE_SCOPE, &rolegroup_ref.role, &rolegroup_ref.role_group, )) From 20e24ef1d3970c45408430835c6d2a243b820f7b Mon Sep 17 00:00:00 2001 From: Malte Sander Date: Tue, 13 Dec 2022 11:50:28 +0100 Subject: [PATCH 13/19] fixed test --- tests/templates/kuttl/upgrade/03-assert.yaml.j2 | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/templates/kuttl/upgrade/03-assert.yaml.j2 b/tests/templates/kuttl/upgrade/03-assert.yaml.j2 index bf6c8197..0e843264 100644 --- a/tests/templates/kuttl/upgrade/03-assert.yaml.j2 +++ b/tests/templates/kuttl/upgrade/03-assert.yaml.j2 @@ -8,7 +8,7 @@ kind: StatefulSet metadata: name: simple-kafka-broker-default labels: - app.kubernetes.io/version: {{ test_scenario['values']['upgrade_new'] }} + app.kubernetes.io/version: "{{ test_scenario['values']['upgrade_new'].split('-stackable')[0] }}" status: readyReplicas: 1 replicas: 1 From 32528d9c205da2d3c48921ccd78b7340c5a72707 Mon Sep 17 00:00:00 2001 From: Malte Sander Date: Tue, 13 Dec 2022 11:50:37 +0100 Subject: [PATCH 14/19] fixed docs --- docs/modules/ROOT/pages/usage.adoc | 24 ++++++++++++++----- .../getting_started/examples/code/kafka.yaml | 4 +++- 2 files changed, 21 insertions(+), 7 deletions(-) diff --git a/docs/modules/ROOT/pages/usage.adoc b/docs/modules/ROOT/pages/usage.adoc index bbf812fa..fcfb93e9 100644 --- a/docs/modules/ROOT/pages/usage.adoc +++ b/docs/modules/ROOT/pages/usage.adoc @@ -23,7 +23,9 @@ kind: KafkaCluster metadata: name: simple-kafka spec: - version: 3.2.0-stackable0.2.0 + image: + productVersion: 3.2.0 + stackableVersion: 0.2.0 zookeeperConfigMapName: simple-kafka-znode brokers: roleGroups: @@ -40,7 +42,9 @@ kind: KafkaCluster metadata: name: simple-kafka spec: - version: 3.2.0-stackable0.2.0 + image: + productVersion: 3.2.0 + stackableVersion: 0.2.0 zookeeperConfigMapName: simple-kafka-znode opa: configMapName: simple-opa @@ -61,7 +65,9 @@ kind: KafkaCluster metadata: name: simple-kafka spec: - version: 3.2.0-stackable0.2.0 + image: + productVersion: 3.2.0 + stackableVersion: 0.2.0 zookeeperConfigMapName: simple-kafka-znode opa: configMapName: simple-opa @@ -96,7 +102,9 @@ kind: KafkaCluster metadata: name: simple-kafka spec: - version: 3.2.0-stackable0.2.0 + image: + productVersion: 3.2.0 + stackableVersion: 0.2.0 zookeeperConfigMapName: simple-kafka-znode log4j: |- log4j.rootLogger=INFO, stdout, kafkaAppender @@ -128,7 +136,9 @@ kind: KafkaCluster metadata: name: simple-kafka spec: - version: 3.2.0-stackable0.2.0 + image: + productVersion: 3.2.0 + stackableVersion: 0.2.0 zookeeperConfigMapName: simple-kafka-znode config: tls: @@ -198,7 +208,9 @@ kind: KafkaCluster metadata: name: simple-kafka spec: - version: 3.2.0-stackable0.2.0 + image: + productVersion: 3.2.0 + stackableVersion: 0.2.0 zookeeperConfigMapName: simple-kafka-znode config: tls: diff --git a/docs/modules/getting_started/examples/code/kafka.yaml b/docs/modules/getting_started/examples/code/kafka.yaml index 1b27a3e7..3f43392f 100644 --- a/docs/modules/getting_started/examples/code/kafka.yaml +++ b/docs/modules/getting_started/examples/code/kafka.yaml @@ -4,7 +4,9 @@ kind: KafkaCluster metadata: name: simple-kafka spec: - version: 3.3.1-stackable0.2.0 + image: + productVersion: 3.3.1 + stackableVersion: 0.2.0 zookeeperConfigMapName: simple-kafka-znode config: tls: null From 87832edaafac660e20adf47daf1898e8c3f71a33 Mon Sep 17 00:00:00 2001 From: Malte Sander Date: Tue, 13 Dec 2022 11:50:42 +0100 Subject: [PATCH 15/19] adapted changelog --- CHANGELOG.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index e58c07c5..71a21fca 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -9,7 +9,9 @@ All notable changes to this project will be documented in this file. - Updated stackable image versions ([#513]). - operator-rs: 0.26.0 -> 0.27.1 ([#519]). - Don't run init container as root and avoid chmod and chowning ([#524]). +- [BREAKING] Use Product image selection instead of version. `spec.version` has been replaced by `spec.image` ([#482]). +[#482]: https://github.com/stackabletech/kafka-operator/pull/482 [#513]: https://github.com/stackabletech/kafka-operator/pull/513 [#519]: https://github.com/stackabletech/kafka-operator/pull/519 [#524]: https://github.com/stackabletech/kafka-operator/pull/524 From 9b33fb7e6410832169da815ba746fc6c95941ac3 Mon Sep 17 00:00:00 2001 From: Malte Sander Date: Tue, 13 Dec 2022 11:53:12 +0100 Subject: [PATCH 16/19] adapted more docs --- .../modules/ROOT/pages/config_properties.adoc | 27 +++++++++++-------- 1 file changed, 16 insertions(+), 11 deletions(-) diff --git a/docs/modules/ROOT/pages/config_properties.adoc b/docs/modules/ROOT/pages/config_properties.adoc index 4946e70e..308fa646 100644 --- a/docs/modules/ROOT/pages/config_properties.adoc +++ b/docs/modules/ROOT/pages/config_properties.adoc @@ -2,17 +2,22 @@ The cluster can be configured via a YAML file. This custom resource specifies the amount of replicas for each role group, role group or role specific configuration like port definitions etc. - apiVersion: kafka.stackable.tech/v1alpha1 - kind: KafkaCluster - metadata: - name: simple-kafka - spec: - version: 3.2.0-stackable0.2.0 - zookeeperConfigMapName: simple-kafka-znode - brokers: - roleGroups: - default: - replicas: 1 +[source,yaml] +---- +apiVersion: kafka.stackable.tech/v1alpha1 +kind: KafkaCluster +metadata: + name: simple-kafka +spec: + image: + productVersion: 3.3.1 + stackableVersion: 0.2.0 + zookeeperConfigMapName: simple-kafka-znode + brokers: + roleGroups: + default: + replicas: 1 +---- === Structure From 6b741a695e5ff0e89840d4370e20af466c80f756 Mon Sep 17 00:00:00 2001 From: Malte Sander Date: Tue, 13 Dec 2022 11:53:20 +0100 Subject: [PATCH 17/19] adapted readme --- .readme/partials/main.md.j2 | 4 +++- README.md | 4 +++- 2 files changed, 6 insertions(+), 2 deletions(-) diff --git a/.readme/partials/main.md.j2 b/.readme/partials/main.md.j2 index e695f00a..79488c22 100644 --- a/.readme/partials/main.md.j2 +++ b/.readme/partials/main.md.j2 @@ -27,7 +27,9 @@ kind: KafkaCluster metadata: name: simple-kafka spec: - version: 3.2.0-stackable0.2.0 + image: + productVersion: 3.3.1 + stackableVersion: 0.2.0 zookeeperConfigMapName: simple-kafka-znode config: tls: null diff --git a/README.md b/README.md index 06af7b1c..e2c298ba 100644 --- a/README.md +++ b/README.md @@ -47,7 +47,9 @@ kind: KafkaCluster metadata: name: simple-kafka spec: - version: 3.2.0-stackable0.2.0 + image: + productVersion: 3.3.1 + stackableVersion: 0.2.0 zookeeperConfigMapName: simple-kafka-znode config: tls: null From b0469ee12d17025b94e968402e8dd5b6256d0343 Mon Sep 17 00:00:00 2001 From: Malte Sander Date: Tue, 13 Dec 2022 12:02:07 +0100 Subject: [PATCH 18/19] Apply suggestions from code review Co-authored-by: Sebastian Bernauer --- rust/operator/src/kafka_controller.rs | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/rust/operator/src/kafka_controller.rs b/rust/operator/src/kafka_controller.rs index c3e8c5bd..5f0a7a39 100644 --- a/rust/operator/src/kafka_controller.rs +++ b/rust/operator/src/kafka_controller.rs @@ -419,7 +419,7 @@ pub fn build_broker_role_service( .with_recommended_labels(build_recommended_labels( kafka, KAFKA_CONTROLLER_NAME, - &resolved_product_image.product_version, + &resolved_product_image.app_version_label, &role_name, "global", )) @@ -450,7 +450,7 @@ fn build_broker_role_serviceaccount( .with_recommended_labels(build_recommended_labels( kafka, KAFKA_CONTROLLER_NAME, - &resolved_product_image.product_version, + &resolved_product_image.app_version_label, &role_name, "global", )) @@ -467,7 +467,7 @@ fn build_broker_role_serviceaccount( .with_recommended_labels(build_recommended_labels( kafka, KAFKA_CONTROLLER_NAME, - &resolved_product_image.product_version, + &resolved_product_image.app_version_label, &role_name, "global", )) @@ -512,7 +512,7 @@ fn build_broker_rolegroup_config_map( .with_recommended_labels(build_recommended_labels( kafka, KAFKA_CONTROLLER_NAME, - &resolved_product_image.product_version, + &resolved_product_image.app_version_label, &rolegroup.role, "global", )) @@ -553,7 +553,7 @@ fn build_broker_rolegroup_service( .with_recommended_labels(build_recommended_labels( kafka, KAFKA_CONTROLLER_NAME, - &resolved_product_image.product_version, + &resolved_product_image.app_version_label, &rolegroup.role, &rolegroup.role_group, )) @@ -835,7 +835,7 @@ fn build_broker_rolegroup_statefulset( m.with_recommended_labels(build_recommended_labels( kafka, KAFKA_CONTROLLER_NAME, - &resolved_product_image.product_version, + &resolved_product_image.app_version_label, &rolegroup_ref.role, &rolegroup_ref.role_group, )) @@ -884,7 +884,7 @@ fn build_broker_rolegroup_statefulset( .with_recommended_labels(build_recommended_labels( kafka, KAFKA_CONTROLLER_NAME, - &resolved_product_image.product_version, + &resolved_product_image.app_version_label, &rolegroup_ref.role, &rolegroup_ref.role_group, )) From da78fbb66a2d2a773c1958cf00b5b69cdf725010 Mon Sep 17 00:00:00 2001 From: Malte Sander Date: Tue, 13 Dec 2022 12:15:57 +0100 Subject: [PATCH 19/19] reverted test fix --- tests/templates/kuttl/upgrade/03-assert.yaml.j2 | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/templates/kuttl/upgrade/03-assert.yaml.j2 b/tests/templates/kuttl/upgrade/03-assert.yaml.j2 index 0e843264..c8ec1d77 100644 --- a/tests/templates/kuttl/upgrade/03-assert.yaml.j2 +++ b/tests/templates/kuttl/upgrade/03-assert.yaml.j2 @@ -8,7 +8,7 @@ kind: StatefulSet metadata: name: simple-kafka-broker-default labels: - app.kubernetes.io/version: "{{ test_scenario['values']['upgrade_new'].split('-stackable')[0] }}" + app.kubernetes.io/version: "{{ test_scenario['values']['upgrade_new'] }}" status: readyReplicas: 1 replicas: 1