From b1a89b88bdcd02b20c9eeffa1c4df09f76916be7 Mon Sep 17 00:00:00 2001 From: Stacky McStackface Date: Wed, 1 Dec 2021 08:12:20 +0000 Subject: [PATCH 1/2] Generated commit to update templated files based on rev 3f7a2f8 in stackabletech/operator-templating repo. Original commit message: Removed buggy echo line (#27) --- .github/workflows/pr_generate_manifests.yml | 33 +++++++++++++++++++++ Makefile | 8 +++++ deploy/manifests/Kustomization | 11 +++++++ scripts/generate-manifests.sh | 22 ++++++++++++++ 4 files changed, 74 insertions(+) create mode 100644 .github/workflows/pr_generate_manifests.yml create mode 100644 deploy/manifests/Kustomization create mode 100755 scripts/generate-manifests.sh diff --git a/.github/workflows/pr_generate_manifests.yml b/.github/workflows/pr_generate_manifests.yml new file mode 100644 index 00000000..8ea9b183 --- /dev/null +++ b/.github/workflows/pr_generate_manifests.yml @@ -0,0 +1,33 @@ +# ============= +# This file is automatically generated from the templates in stackabletech/operator-templating +# DON'T MANUALLY EDIT THIS FILE +# ============= +name: Update Manifest files + +on: + pull_request: + +jobs: + manifests: + runs-on: ubuntu-latest + steps: + - name: Checkout + uses: actions/checkout@v2 + with: + token: ${{ secrets.STACKY_MC_STACKFACE_TOKEN }} + - name: Set up Helm + uses: azure/setup-helm@v1 + with: + version: v3.6.2 + - name: update manifests + run: make generate-manifests + - name: Add & Commit + uses: EndBug/add-and-commit@v7 + with: + default_author: user_info + author_name: Stacky McStackface + author_email: stackable-bot@users.noreply.github.com + pathspec_error_handling: exitImmediately + pull: NO-PULL + add: 'deploy' + message: 'Github Actions: Generated k8s manifest files' diff --git a/Makefile b/Makefile index b122258e..ff3c75c9 100644 --- a/Makefile +++ b/Makefile @@ -38,3 +38,11 @@ deploy/helm/kafka-operator/crds/crds.yaml: chart-lint: compile-chart docker run -it -v $(shell pwd):/build/helm-charts -w /build/helm-charts quay.io/helmpack/chart-testing:v3.4.0 ct lint --config deploy/helm/chart_testing.yaml + +## Manifest related targets +clean-manifests: + mkdir -p deploy/manifests + rm -rf $$(find deploy/manifests -maxdepth 1 -mindepth 1 -not -name Kustomization) + +generate-manifests: clean-manifests compile-chart + ./scripts/generate-manifests.sh diff --git a/deploy/manifests/Kustomization b/deploy/manifests/Kustomization new file mode 100644 index 00000000..336cdb27 --- /dev/null +++ b/deploy/manifests/Kustomization @@ -0,0 +1,11 @@ +# ============= +# This file is automatically generated from the templates in stackabletech/operator-templating +# DON'T MANUALLY EDIT THIS FILE +# ============= +apiVersion: kustomize.config.k8s.io/v1beta1 +kind: Kustomization +resources: + - configmap.yaml + - deployment.yaml + - roles.yaml + - serviceaccount.yaml diff --git a/scripts/generate-manifests.sh b/scripts/generate-manifests.sh new file mode 100755 index 00000000..0510e840 --- /dev/null +++ b/scripts/generate-manifests.sh @@ -0,0 +1,22 @@ +#!/bin/bash +# This script reads a Helm chart from deploy/helm/kafka-operator and +# generates manifest files into deploy/manifestss +set -e + +tmp=$(mktemp -d ./manifests-XXXXX) + +helm template --output-dir $tmp \ + --include-crds \ + --name-template kafka-operator \ + deploy/helm/kafka-operator + +for file in $(find $tmp -type f) +do + yq eval -i 'del(.. | select(has("app.kubernetes.io/managed-by")) | ."app.kubernetes.io/managed-by")' $file + yq eval -i 'del(.. | select(has("helm.sh/chart")) | ."helm.sh/chart")' $file + sed -i '/# Source: .*/d' $file +done + +cp -r $tmp/kafka-operator/*/* deploy/manifests/ + +rm -rf $tmp From 5b7313b3b5e6d044b3e8ad34b3f8c71e696ba9a9 Mon Sep 17 00:00:00 2001 From: Stacky McStackface Date: Wed, 1 Dec 2021 08:13:17 +0000 Subject: [PATCH 2/2] Github Actions: Generated k8s manifest files --- deploy/helm/kafka-operator/Chart.yaml | 9 +- .../kafka-operator/configs/properties.yaml | 174 ++++++ deploy/helm/kafka-operator/crds/crds.yaml | 495 +++++++++++++++++ deploy/manifests/configmap.yaml | 189 +++++++ deploy/manifests/crds.yaml | 496 ++++++++++++++++++ deploy/manifests/deployment.yaml | 42 ++ deploy/manifests/roles.yaml | 95 ++++ deploy/manifests/serviceaccount.yaml | 31 ++ 8 files changed, 1524 insertions(+), 7 deletions(-) create mode 100644 deploy/helm/kafka-operator/configs/properties.yaml create mode 100644 deploy/helm/kafka-operator/crds/crds.yaml create mode 100644 deploy/manifests/configmap.yaml create mode 100644 deploy/manifests/crds.yaml create mode 100644 deploy/manifests/deployment.yaml create mode 100644 deploy/manifests/roles.yaml create mode 100644 deploy/manifests/serviceaccount.yaml diff --git a/deploy/helm/kafka-operator/Chart.yaml b/deploy/helm/kafka-operator/Chart.yaml index 609849ff..c424802a 100644 --- a/deploy/helm/kafka-operator/Chart.yaml +++ b/deploy/helm/kafka-operator/Chart.yaml @@ -2,11 +2,9 @@ # This file is automatically generated from the templates in stackabletech/operator-templating # DON'T MANUALLY EDIT THIS FILE # ============= - apiVersion: v2 name: kafka-operator description: The Stackable Operator for Apache Kafka - # A chart can be either an 'application' or a 'library' chart. # # Application charts are a collection of templates that can be packaged into versioned archives @@ -16,18 +14,15 @@ description: The Stackable Operator for Apache Kafka # a dependency of application charts to inject those utilities and functions into the rendering # pipeline. Library charts do not define any templates and therefore cannot be deployed. type: application - maintainers: - name: stackable url: github.com/stackabletech - # This is the chart version. This version number should be incremented each time you make changes # to the chart and its templates, including the app version. # Versions are expected to follow Semantic Versioning (https://semver.org/) -version: - +version: 0.4.0-nightly # This is the version number of the application being deployed. This version number should be # incremented each time you make changes to the application. Versions are not expected to # follow Semantic Versioning. They should reflect the version the application is using. # It is recommended to use it with quotes. -appVersion: +appVersion: 0.4.0-nightly diff --git a/deploy/helm/kafka-operator/configs/properties.yaml b/deploy/helm/kafka-operator/configs/properties.yaml new file mode 100644 index 00000000..7ac7feeb --- /dev/null +++ b/deploy/helm/kafka-operator/configs/properties.yaml @@ -0,0 +1,174 @@ +version: 0.1.0 +spec: + units: + - unit: &unitPort + name: "port" + regex: "^([0-9]{1,4}|[1-5][0-9]{4}|6[0-4][0-9]{3}|65[0-4][0-9]{2}|655[0-2][0-9]|6553[0-5])$" + + - unit: &unitUrl + name: "url" + regex: "^((https?|ftp|file)://)?[-a-zA-Z0-9+&@#}/%?=~_|!:,.;]*[-a-zA-Z0-9+&@#/%=~_|]" + examples: + - "https://www.stackable.de/blog/" + + - unit: &unitCapacity + name: "capacity" + regex: "^[1-9]\\d*$" + + - unit: &unitMilliseconds + name: "milliseconds" + regex: "^[1-9]\\d*$" + +properties: + - property: &zookeeperConnect + propertyNames: + - name: "zookeeper.connect" + kind: + type: "file" + file: "server.properties" + datatype: + type: "string" + unit: *unitUrl + defaultValues: + - fromVersion: "0.0.0" + value: "localhost:2181" + roles: + - name: "broker" + required: true + asOfVersion: "0.0.0" + description: "The zookeeper connection string" + + - property: &zookeeperTimeout + propertyNames: + - name: "zookeeper.connection.timeout.ms" + kind: + type: "file" + file: "server.properties" + datatype: + type: "integer" + unit: *unitMilliseconds + defaultValues: + - fromVersion: "0.0.0" + value: "18000" + roles: + - name: "broker" + required: true + asOfVersion: "0.0.0" + description: "Zookeeper connection timeout in milliseconds." + + - property: &opaAuthorizerClassName + propertyNames: + - name: "authorizer.class.name" + kind: + type: "file" + file: "server.properties" + datatype: + type: "string" + defaultValues: + - fromVersion: "0.0.0" + value: "com.bisnode.kafka.authorization.OpaAuthorizer" + roles: + - name: "broker" + required: false + asOfVersion: "0.0.0" + description: "OPA Authorizer class name" + + - property: &opaAuthorizerUrl + propertyNames: + - name: "opa.authorizer.url" + kind: + type: "file" + file: "server.properties" + datatype: + type: "string" + unit: *unitUrl + roles: + - name: "broker" + required: false + asOfVersion: "0.0.0" + description: "OPA Authorizer URL" + + - property: &opaAuthorizerInitialCacheCapacity + propertyNames: + - name: "opa.authorizer.cache.initial.capacity" + kind: + type: "file" + file: "server.properties" + datatype: + type: "integer" + unit: *unitCapacity + defaultValues: + - fromVersion: "0.0.0" + value: "0" + roles: + - name: "broker" + required: false + asOfVersion: "0.0.0" + description: "OPA Authorizer initial cache capacity" + + - property: &opaAuthorizerMaxCacheSize + propertyNames: + - name: "opa.authorizer.cache.maximum.size" + kind: + type: "file" + file: "server.properties" + datatype: + type: "integer" + unit: *unitCapacity + defaultValues: + - fromVersion: "0.0.0" + value: "0" + roles: + - name: "broker" + required: false + asOfVersion: "0.0.0" + description: "OPA authorizer max cache size" + + - property: &opaAuthorizerCacheExpireAfterSeconds + propertyNames: + - name: "opa.authorizer.cache.expire.after.seconds" + kind: + type: "file" + file: "server.properties" + datatype: + type: "integer" + unit: *unitCapacity + defaultValues: + - fromVersion: "0.0.0" + value: "0" + roles: + - name: "broker" + required: false + asOfVersion: "0.0.0" + description: "The number of seconds after which the OPA authorizer cache expires" + + - property: &logDirs + propertyNames: + - name: "log.dirs" + kind: + type: "file" + file: "server.properties" + datatype: + type: "string" + roles: + - name: "server" + required: false + asOfVersion: "0.0.0" + description: "A comma separated list of directories under which to store log files" + + - property: &metricsPort + propertyNames: + - name: "metricsPort" + kind: + type: "env" + datatype: + type: "integer" + unit: *unitPort + min: "1024" + max: "65535" + roles: + - name: "server" + required: false + asOfVersion: "0.0.0" + description: "The port where Kafka metrics are exposed as a Prometheus endpoint." + diff --git a/deploy/helm/kafka-operator/crds/crds.yaml b/deploy/helm/kafka-operator/crds/crds.yaml new file mode 100644 index 00000000..63f22407 --- /dev/null +++ b/deploy/helm/kafka-operator/crds/crds.yaml @@ -0,0 +1,495 @@ +--- +apiVersion: apiextensions.k8s.io/v1 +kind: CustomResourceDefinition +metadata: + name: kafkaclusters.kafka.stackable.tech + annotations: + helm.sh/resource-policy: keep +spec: + group: kafka.stackable.tech + names: + categories: [] + kind: KafkaCluster + plural: kafkaclusters + shortNames: + - kafka + singular: kafkacluster + scope: Namespaced + versions: + - additionalPrinterColumns: [] + name: v1alpha1 + schema: + openAPIV3Schema: + description: "Auto-generated derived type for KafkaClusterSpec via `CustomResource`" + properties: + spec: + properties: + brokers: + properties: + cliOverrides: + additionalProperties: + type: string + nullable: true + type: object + config: + description: "In order for compute_files from the Configuration trait to work, we cannot pass an empty or \"None\" config. Therefore we need at least one required property." + nullable: true + properties: + logDirs: + type: string + metricsPort: + format: uint16 + minimum: 0.0 + nullable: true + type: integer + required: + - logDirs + type: object + configOverrides: + additionalProperties: + additionalProperties: + type: string + type: object + nullable: true + type: object + envOverrides: + additionalProperties: + type: string + nullable: true + type: object + roleGroups: + additionalProperties: + properties: + cliOverrides: + additionalProperties: + type: string + nullable: true + type: object + config: + description: "In order for compute_files from the Configuration trait to work, we cannot pass an empty or \"None\" config. Therefore we need at least one required property." + nullable: true + properties: + logDirs: + type: string + metricsPort: + format: uint16 + minimum: 0.0 + nullable: true + type: integer + required: + - logDirs + type: object + configOverrides: + additionalProperties: + additionalProperties: + type: string + type: object + nullable: true + type: object + envOverrides: + additionalProperties: + type: string + nullable: true + 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 + required: + - roleGroups + type: object + opa: + description: "Contains all data to combine with OPA. The \"opa.authorizer.url\" is set dynamically in the controller (local nodes first, random otherwise)." + nullable: true + properties: + authorizerCacheExpireAfterSeconds: + format: uint + minimum: 0.0 + nullable: true + type: integer + authorizerCacheInitialCapacity: + format: uint + minimum: 0.0 + nullable: true + type: integer + authorizerCacheMaximumSize: + format: uint + minimum: 0.0 + nullable: true + type: integer + authorizerClassName: + type: string + reference: + description: Contains all necessary information to identify a Stackable managed Open Policy Agent (OPA) and build a connection string for it. The main purpose for this struct is for other operators that need to reference an OPA to use in their CRDs. This has the benefit of keeping references to OPA consistent throughout the entire stack. + properties: + name: + type: string + namespace: + type: string + required: + - name + - namespace + type: object + required: + - authorizerClassName + - reference + type: object + version: + properties: + kafka_version: + type: string + scala_version: + nullable: true + type: string + required: + - kafka_version + type: object + zookeeperReference: + description: Contains all necessary information identify a Stackable managed ZooKeeper ensemble and build a connection string for it. The main purpose for this struct is for other operators that need to reference a ZooKeeper ensemble to use in their CRDs. This has the benefit of keeping references to Zookeeper ensembles consistent throughout the entire stack. + properties: + chroot: + nullable: true + type: string + name: + type: string + namespace: + type: string + required: + - name + - namespace + type: object + required: + - brokers + - version + - zookeeperReference + type: object + status: + nullable: true + properties: + clusterExecutionStatus: + description: Signals the current status of the cluster + enum: + - Stopped + - Running + nullable: true + type: string + conditions: + items: + description: Condition contains details for one aspect of the current state of this API Resource. + properties: + lastTransitionTime: + description: "lastTransitionTime is the last time the condition transitioned from one status to another. This should be when the underlying condition changed. If that is not known, then using the time when the API field changed is acceptable." + format: date-time + type: string + message: + description: message is a human readable message indicating details about the transition. This may be an empty string. + type: string + observedGeneration: + description: "observedGeneration represents the .metadata.generation that the condition was set based upon. For instance, if .metadata.generation is currently 12, but the .status.conditions[x].observedGeneration is 9, the condition is out of date with respect to the current state of the instance." + format: int64 + type: integer + reason: + description: "reason contains a programmatic identifier indicating the reason for the condition's last transition. Producers of specific condition types may define expected values and meanings for this field, and whether the values are considered a guaranteed API. The value should be a CamelCase string. This field may not be empty." + type: string + status: + description: "status of the condition, one of True, False, Unknown." + type: string + type: + description: type of condition in CamelCase or in foo.example.com/CamelCase. + type: string + required: + - lastTransitionTime + - message + - reason + - status + - type + type: object + type: array + currentCommand: + nullable: true + properties: + kind: + type: string + name: + type: string + namespace: + type: string + uid: + type: string + required: + - kind + - name + - namespace + - uid + type: object + history: + nullable: true + properties: + mapping: + additionalProperties: + properties: + name: + type: string + required: + - name + type: object + type: object + required: + - mapping + type: object + version: + description: The version of the product provided by the operator. Split into current and target version in order track upgrading and downgrading progress. + nullable: true + properties: + current: + nullable: true + properties: + kafka_version: + type: string + scala_version: + nullable: true + type: string + required: + - kafka_version + type: object + target: + nullable: true + properties: + kafka_version: + type: string + scala_version: + nullable: true + type: string + required: + - kafka_version + type: object + type: object + type: object + required: + - spec + title: KafkaCluster + type: object + served: true + storage: true + subresources: + status: {} +--- +apiVersion: apiextensions.k8s.io/v1 +kind: CustomResourceDefinition +metadata: + name: restarts.command.kafka.stackable.tech + annotations: + helm.sh/resource-policy: keep +spec: + group: command.kafka.stackable.tech + names: + categories: [] + kind: Restart + plural: restarts + shortNames: [] + singular: restart + scope: Namespaced + versions: + - additionalPrinterColumns: [] + name: v1alpha1 + schema: + openAPIV3Schema: + description: "Auto-generated derived type for RestartCommandSpec via `CustomResource`" + properties: + spec: + properties: + name: + type: string + roles: + items: + enum: + - Broker + type: string + nullable: true + type: array + rolling: + type: boolean + required: + - name + - rolling + type: object + status: + nullable: true + properties: + finishedAt: + description: Time is a wrapper around time.Time which supports correct marshaling to YAML and JSON. Wrappers are provided for many of the factory methods that the time package offers. + format: date-time + nullable: true + type: string + startedAt: + description: Time is a wrapper around time.Time which supports correct marshaling to YAML and JSON. Wrappers are provided for many of the factory methods that the time package offers. + format: date-time + nullable: true + type: string + type: object + required: + - spec + title: Restart + type: object + served: true + storage: true + subresources: + status: {} +--- +apiVersion: apiextensions.k8s.io/v1 +kind: CustomResourceDefinition +metadata: + name: starts.command.kafka.stackable.tech + annotations: + helm.sh/resource-policy: keep +spec: + group: command.kafka.stackable.tech + names: + categories: [] + kind: Start + plural: starts + shortNames: [] + singular: start + scope: Namespaced + versions: + - additionalPrinterColumns: [] + name: v1alpha1 + schema: + openAPIV3Schema: + description: "Auto-generated derived type for StartCommandSpec via `CustomResource`" + properties: + spec: + properties: + name: + type: string + roles: + items: + enum: + - Broker + type: string + nullable: true + type: array + rolling: + type: boolean + required: + - name + - rolling + type: object + status: + nullable: true + properties: + finishedAt: + description: Time is a wrapper around time.Time which supports correct marshaling to YAML and JSON. Wrappers are provided for many of the factory methods that the time package offers. + format: date-time + nullable: true + type: string + startedAt: + description: Time is a wrapper around time.Time which supports correct marshaling to YAML and JSON. Wrappers are provided for many of the factory methods that the time package offers. + format: date-time + nullable: true + type: string + type: object + required: + - spec + title: Start + type: object + served: true + storage: true + subresources: + status: {} +--- +apiVersion: apiextensions.k8s.io/v1 +kind: CustomResourceDefinition +metadata: + name: stops.command.kafka.stackable.tech + annotations: + helm.sh/resource-policy: keep +spec: + group: command.kafka.stackable.tech + names: + categories: [] + kind: Stop + plural: stops + shortNames: [] + singular: stop + scope: Namespaced + versions: + - additionalPrinterColumns: [] + name: v1alpha1 + schema: + openAPIV3Schema: + description: "Auto-generated derived type for StopCommandSpec via `CustomResource`" + properties: + spec: + properties: + name: + type: string + roles: + items: + enum: + - Broker + type: string + nullable: true + type: array + rolling: + type: boolean + required: + - name + - rolling + type: object + status: + nullable: true + properties: + finishedAt: + description: Time is a wrapper around time.Time which supports correct marshaling to YAML and JSON. Wrappers are provided for many of the factory methods that the time package offers. + format: date-time + nullable: true + type: string + startedAt: + description: Time is a wrapper around time.Time which supports correct marshaling to YAML and JSON. Wrappers are provided for many of the factory methods that the time package offers. + format: date-time + nullable: true + type: string + type: object + required: + - spec + title: Stop + type: object + served: true + storage: true + subresources: + status: {} diff --git a/deploy/manifests/configmap.yaml b/deploy/manifests/configmap.yaml new file mode 100644 index 00000000..4a93bf0e --- /dev/null +++ b/deploy/manifests/configmap.yaml @@ -0,0 +1,189 @@ +--- +# ============= +# This file is automatically generated from the templates in stackabletech/operator-templating +# DON'T MANUALLY EDIT THIS FILE +# ============= +apiVersion: v1 +data: + properties.yaml: |+ + version: 0.1.0 + spec: + units: + - unit: &unitPort + name: "port" + regex: "^([0-9]{1,4}|[1-5][0-9]{4}|6[0-4][0-9]{3}|65[0-4][0-9]{2}|655[0-2][0-9]|6553[0-5])$" + + - unit: &unitUrl + name: "url" + regex: "^((https?|ftp|file)://)?[-a-zA-Z0-9+&@#}/%?=~_|!:,.;]*[-a-zA-Z0-9+&@#/%=~_|]" + examples: + - "https://www.stackable.de/blog/" + + - unit: &unitCapacity + name: "capacity" + regex: "^[1-9]\\d*$" + + - unit: &unitMilliseconds + name: "milliseconds" + regex: "^[1-9]\\d*$" + + properties: + - property: &zookeeperConnect + propertyNames: + - name: "zookeeper.connect" + kind: + type: "file" + file: "server.properties" + datatype: + type: "string" + unit: *unitUrl + defaultValues: + - fromVersion: "0.0.0" + value: "localhost:2181" + roles: + - name: "broker" + required: true + asOfVersion: "0.0.0" + description: "The zookeeper connection string" + + - property: &zookeeperTimeout + propertyNames: + - name: "zookeeper.connection.timeout.ms" + kind: + type: "file" + file: "server.properties" + datatype: + type: "integer" + unit: *unitMilliseconds + defaultValues: + - fromVersion: "0.0.0" + value: "18000" + roles: + - name: "broker" + required: true + asOfVersion: "0.0.0" + description: "Zookeeper connection timeout in milliseconds." + + - property: &opaAuthorizerClassName + propertyNames: + - name: "authorizer.class.name" + kind: + type: "file" + file: "server.properties" + datatype: + type: "string" + defaultValues: + - fromVersion: "0.0.0" + value: "com.bisnode.kafka.authorization.OpaAuthorizer" + roles: + - name: "broker" + required: false + asOfVersion: "0.0.0" + description: "OPA Authorizer class name" + + - property: &opaAuthorizerUrl + propertyNames: + - name: "opa.authorizer.url" + kind: + type: "file" + file: "server.properties" + datatype: + type: "string" + unit: *unitUrl + roles: + - name: "broker" + required: false + asOfVersion: "0.0.0" + description: "OPA Authorizer URL" + + - property: &opaAuthorizerInitialCacheCapacity + propertyNames: + - name: "opa.authorizer.cache.initial.capacity" + kind: + type: "file" + file: "server.properties" + datatype: + type: "integer" + unit: *unitCapacity + defaultValues: + - fromVersion: "0.0.0" + value: "0" + roles: + - name: "broker" + required: false + asOfVersion: "0.0.0" + description: "OPA Authorizer initial cache capacity" + + - property: &opaAuthorizerMaxCacheSize + propertyNames: + - name: "opa.authorizer.cache.maximum.size" + kind: + type: "file" + file: "server.properties" + datatype: + type: "integer" + unit: *unitCapacity + defaultValues: + - fromVersion: "0.0.0" + value: "0" + roles: + - name: "broker" + required: false + asOfVersion: "0.0.0" + description: "OPA authorizer max cache size" + + - property: &opaAuthorizerCacheExpireAfterSeconds + propertyNames: + - name: "opa.authorizer.cache.expire.after.seconds" + kind: + type: "file" + file: "server.properties" + datatype: + type: "integer" + unit: *unitCapacity + defaultValues: + - fromVersion: "0.0.0" + value: "0" + roles: + - name: "broker" + required: false + asOfVersion: "0.0.0" + description: "The number of seconds after which the OPA authorizer cache expires" + + - property: &logDirs + propertyNames: + - name: "log.dirs" + kind: + type: "file" + file: "server.properties" + datatype: + type: "string" + roles: + - name: "server" + required: false + asOfVersion: "0.0.0" + description: "A comma separated list of directories under which to store log files" + + - property: &metricsPort + propertyNames: + - name: "metricsPort" + kind: + type: "env" + datatype: + type: "integer" + unit: *unitPort + min: "1024" + max: "65535" + roles: + - name: "server" + required: false + asOfVersion: "0.0.0" + description: "The port where Kafka metrics are exposed as a Prometheus endpoint." + +kind: ConfigMap +metadata: + name: kafka-operator-configmap + labels: + app.kubernetes.io/name: kafka-operator + app.kubernetes.io/instance: kafka-operator + app.kubernetes.io/version: "0.4.0-nightly" diff --git a/deploy/manifests/crds.yaml b/deploy/manifests/crds.yaml new file mode 100644 index 00000000..bdb514b1 --- /dev/null +++ b/deploy/manifests/crds.yaml @@ -0,0 +1,496 @@ +--- +--- +apiVersion: apiextensions.k8s.io/v1 +kind: CustomResourceDefinition +metadata: + name: kafkaclusters.kafka.stackable.tech + annotations: + helm.sh/resource-policy: keep +spec: + group: kafka.stackable.tech + names: + categories: [] + kind: KafkaCluster + plural: kafkaclusters + shortNames: + - kafka + singular: kafkacluster + scope: Namespaced + versions: + - additionalPrinterColumns: [] + name: v1alpha1 + schema: + openAPIV3Schema: + description: "Auto-generated derived type for KafkaClusterSpec via `CustomResource`" + properties: + spec: + properties: + brokers: + properties: + cliOverrides: + additionalProperties: + type: string + nullable: true + type: object + config: + description: "In order for compute_files from the Configuration trait to work, we cannot pass an empty or \"None\" config. Therefore we need at least one required property." + nullable: true + properties: + logDirs: + type: string + metricsPort: + format: uint16 + minimum: 0.0 + nullable: true + type: integer + required: + - logDirs + type: object + configOverrides: + additionalProperties: + additionalProperties: + type: string + type: object + nullable: true + type: object + envOverrides: + additionalProperties: + type: string + nullable: true + type: object + roleGroups: + additionalProperties: + properties: + cliOverrides: + additionalProperties: + type: string + nullable: true + type: object + config: + description: "In order for compute_files from the Configuration trait to work, we cannot pass an empty or \"None\" config. Therefore we need at least one required property." + nullable: true + properties: + logDirs: + type: string + metricsPort: + format: uint16 + minimum: 0.0 + nullable: true + type: integer + required: + - logDirs + type: object + configOverrides: + additionalProperties: + additionalProperties: + type: string + type: object + nullable: true + type: object + envOverrides: + additionalProperties: + type: string + nullable: true + 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 + required: + - roleGroups + type: object + opa: + description: "Contains all data to combine with OPA. The \"opa.authorizer.url\" is set dynamically in the controller (local nodes first, random otherwise)." + nullable: true + properties: + authorizerCacheExpireAfterSeconds: + format: uint + minimum: 0.0 + nullable: true + type: integer + authorizerCacheInitialCapacity: + format: uint + minimum: 0.0 + nullable: true + type: integer + authorizerCacheMaximumSize: + format: uint + minimum: 0.0 + nullable: true + type: integer + authorizerClassName: + type: string + reference: + description: Contains all necessary information to identify a Stackable managed Open Policy Agent (OPA) and build a connection string for it. The main purpose for this struct is for other operators that need to reference an OPA to use in their CRDs. This has the benefit of keeping references to OPA consistent throughout the entire stack. + properties: + name: + type: string + namespace: + type: string + required: + - name + - namespace + type: object + required: + - authorizerClassName + - reference + type: object + version: + properties: + kafka_version: + type: string + scala_version: + nullable: true + type: string + required: + - kafka_version + type: object + zookeeperReference: + description: Contains all necessary information identify a Stackable managed ZooKeeper ensemble and build a connection string for it. The main purpose for this struct is for other operators that need to reference a ZooKeeper ensemble to use in their CRDs. This has the benefit of keeping references to Zookeeper ensembles consistent throughout the entire stack. + properties: + chroot: + nullable: true + type: string + name: + type: string + namespace: + type: string + required: + - name + - namespace + type: object + required: + - brokers + - version + - zookeeperReference + type: object + status: + nullable: true + properties: + clusterExecutionStatus: + description: Signals the current status of the cluster + enum: + - Stopped + - Running + nullable: true + type: string + conditions: + items: + description: Condition contains details for one aspect of the current state of this API Resource. + properties: + lastTransitionTime: + description: "lastTransitionTime is the last time the condition transitioned from one status to another. This should be when the underlying condition changed. If that is not known, then using the time when the API field changed is acceptable." + format: date-time + type: string + message: + description: message is a human readable message indicating details about the transition. This may be an empty string. + type: string + observedGeneration: + description: "observedGeneration represents the .metadata.generation that the condition was set based upon. For instance, if .metadata.generation is currently 12, but the .status.conditions[x].observedGeneration is 9, the condition is out of date with respect to the current state of the instance." + format: int64 + type: integer + reason: + description: "reason contains a programmatic identifier indicating the reason for the condition's last transition. Producers of specific condition types may define expected values and meanings for this field, and whether the values are considered a guaranteed API. The value should be a CamelCase string. This field may not be empty." + type: string + status: + description: "status of the condition, one of True, False, Unknown." + type: string + type: + description: type of condition in CamelCase or in foo.example.com/CamelCase. + type: string + required: + - lastTransitionTime + - message + - reason + - status + - type + type: object + type: array + currentCommand: + nullable: true + properties: + kind: + type: string + name: + type: string + namespace: + type: string + uid: + type: string + required: + - kind + - name + - namespace + - uid + type: object + history: + nullable: true + properties: + mapping: + additionalProperties: + properties: + name: + type: string + required: + - name + type: object + type: object + required: + - mapping + type: object + version: + description: The version of the product provided by the operator. Split into current and target version in order track upgrading and downgrading progress. + nullable: true + properties: + current: + nullable: true + properties: + kafka_version: + type: string + scala_version: + nullable: true + type: string + required: + - kafka_version + type: object + target: + nullable: true + properties: + kafka_version: + type: string + scala_version: + nullable: true + type: string + required: + - kafka_version + type: object + type: object + type: object + required: + - spec + title: KafkaCluster + type: object + served: true + storage: true + subresources: + status: {} +--- +apiVersion: apiextensions.k8s.io/v1 +kind: CustomResourceDefinition +metadata: + name: restarts.command.kafka.stackable.tech + annotations: + helm.sh/resource-policy: keep +spec: + group: command.kafka.stackable.tech + names: + categories: [] + kind: Restart + plural: restarts + shortNames: [] + singular: restart + scope: Namespaced + versions: + - additionalPrinterColumns: [] + name: v1alpha1 + schema: + openAPIV3Schema: + description: "Auto-generated derived type for RestartCommandSpec via `CustomResource`" + properties: + spec: + properties: + name: + type: string + roles: + items: + enum: + - Broker + type: string + nullable: true + type: array + rolling: + type: boolean + required: + - name + - rolling + type: object + status: + nullable: true + properties: + finishedAt: + description: Time is a wrapper around time.Time which supports correct marshaling to YAML and JSON. Wrappers are provided for many of the factory methods that the time package offers. + format: date-time + nullable: true + type: string + startedAt: + description: Time is a wrapper around time.Time which supports correct marshaling to YAML and JSON. Wrappers are provided for many of the factory methods that the time package offers. + format: date-time + nullable: true + type: string + type: object + required: + - spec + title: Restart + type: object + served: true + storage: true + subresources: + status: {} +--- +apiVersion: apiextensions.k8s.io/v1 +kind: CustomResourceDefinition +metadata: + name: starts.command.kafka.stackable.tech + annotations: + helm.sh/resource-policy: keep +spec: + group: command.kafka.stackable.tech + names: + categories: [] + kind: Start + plural: starts + shortNames: [] + singular: start + scope: Namespaced + versions: + - additionalPrinterColumns: [] + name: v1alpha1 + schema: + openAPIV3Schema: + description: "Auto-generated derived type for StartCommandSpec via `CustomResource`" + properties: + spec: + properties: + name: + type: string + roles: + items: + enum: + - Broker + type: string + nullable: true + type: array + rolling: + type: boolean + required: + - name + - rolling + type: object + status: + nullable: true + properties: + finishedAt: + description: Time is a wrapper around time.Time which supports correct marshaling to YAML and JSON. Wrappers are provided for many of the factory methods that the time package offers. + format: date-time + nullable: true + type: string + startedAt: + description: Time is a wrapper around time.Time which supports correct marshaling to YAML and JSON. Wrappers are provided for many of the factory methods that the time package offers. + format: date-time + nullable: true + type: string + type: object + required: + - spec + title: Start + type: object + served: true + storage: true + subresources: + status: {} +--- +apiVersion: apiextensions.k8s.io/v1 +kind: CustomResourceDefinition +metadata: + name: stops.command.kafka.stackable.tech + annotations: + helm.sh/resource-policy: keep +spec: + group: command.kafka.stackable.tech + names: + categories: [] + kind: Stop + plural: stops + shortNames: [] + singular: stop + scope: Namespaced + versions: + - additionalPrinterColumns: [] + name: v1alpha1 + schema: + openAPIV3Schema: + description: "Auto-generated derived type for StopCommandSpec via `CustomResource`" + properties: + spec: + properties: + name: + type: string + roles: + items: + enum: + - Broker + type: string + nullable: true + type: array + rolling: + type: boolean + required: + - name + - rolling + type: object + status: + nullable: true + properties: + finishedAt: + description: Time is a wrapper around time.Time which supports correct marshaling to YAML and JSON. Wrappers are provided for many of the factory methods that the time package offers. + format: date-time + nullable: true + type: string + startedAt: + description: Time is a wrapper around time.Time which supports correct marshaling to YAML and JSON. Wrappers are provided for many of the factory methods that the time package offers. + format: date-time + nullable: true + type: string + type: object + required: + - spec + title: Stop + type: object + served: true + storage: true + subresources: + status: {} diff --git a/deploy/manifests/deployment.yaml b/deploy/manifests/deployment.yaml new file mode 100644 index 00000000..75309978 --- /dev/null +++ b/deploy/manifests/deployment.yaml @@ -0,0 +1,42 @@ +--- +# ============= +# This file is automatically generated from the templates in stackabletech/operator-templating +# DON'T MANUALLY EDIT THIS FILE +# ============= +apiVersion: apps/v1 +kind: Deployment +metadata: + name: kafka-operator-deployment + labels: + app.kubernetes.io/name: kafka-operator + app.kubernetes.io/instance: kafka-operator + app.kubernetes.io/version: "0.4.0-nightly" +spec: + replicas: 1 + strategy: + type: Recreate + selector: + matchLabels: + app.kubernetes.io/name: kafka-operator + app.kubernetes.io/instance: kafka-operator + template: + metadata: + labels: + app.kubernetes.io/name: kafka-operator + app.kubernetes.io/instance: kafka-operator + spec: + serviceAccountName: kafka-operator-serviceaccount + securityContext: {} + containers: + - name: kafka-operator + securityContext: {} + image: "docker.stackable.tech/stackable/kafka-operator:0.4.0-nightly" + imagePullPolicy: IfNotPresent + resources: {} + volumeMounts: + - mountPath: /etc/stackable/kafka-operator/config-spec + name: config-spec + volumes: + - name: config-spec + configMap: + name: kafka-operator-configmap diff --git a/deploy/manifests/roles.yaml b/deploy/manifests/roles.yaml new file mode 100644 index 00000000..c38e1c35 --- /dev/null +++ b/deploy/manifests/roles.yaml @@ -0,0 +1,95 @@ +--- +apiVersion: rbac.authorization.k8s.io/v1 +kind: ClusterRole +metadata: + name: kafka-operator-clusterrole +rules: + # For Apache ZooKeeper dependents + - apiGroups: + - zookeeper.stackable.tech + resources: + - zookeeperclusters + verbs: + - get + - list + - watch + # For OPA dependents. Note that OPA it's self is listed here because it's own resource name + # doesn't follow the *clusters convention + - apiGroups: + - opa.stackable.tech + resources: + - openpolicyagents + - openpolicyagents/status + - regorules + verbs: + - create + - get + - list + - watch + - patch + - apiGroups: + - "" + resources: + - nodes + verbs: + - list + - watch + - apiGroups: + - "" + resources: + - pods + - configmaps + verbs: + - create + - delete + - list + - watch + - update + - apiGroups: + - batch + resources: + - jobs + verbs: + - create + - get + - list + - watch + - apiGroups: + - apiextensions.k8s.io + resources: + - customresourcedefinitions + verbs: + - get + - apiGroups: + - command.kafka.stackable.tech + resources: + - inits + - restarts + - starts + - stops + verbs: + - get + - list + - patch + - watch + - apiGroups: + - command.kafka.stackable.tech + resources: + - inits/status + verbs: + - patch + - apiGroups: + - kafka.stackable.tech + resources: + - kafkaclusters + verbs: + - get + - list + - patch + - watch + - apiGroups: + - kafka.stackable.tech + resources: + - kafkaclusters/status + verbs: + - patch diff --git a/deploy/manifests/serviceaccount.yaml b/deploy/manifests/serviceaccount.yaml new file mode 100644 index 00000000..d54787db --- /dev/null +++ b/deploy/manifests/serviceaccount.yaml @@ -0,0 +1,31 @@ +--- +# ============= +# This file is automatically generated from the templates in stackabletech/operator-templating +# DON'T MANUALLY EDIT THIS FILE +# ============= +apiVersion: v1 +kind: ServiceAccount +metadata: + name: kafka-operator-serviceaccount + labels: + app.kubernetes.io/name: kafka-operator + app.kubernetes.io/instance: kafka-operator + app.kubernetes.io/version: "0.4.0-nightly" +--- +apiVersion: rbac.authorization.k8s.io/v1 +# This cluster role binding allows anyone in the "manager" group to read secrets in any namespace. +kind: ClusterRoleBinding +metadata: + name: kafka-operator-clusterrolebinding + labels: + app.kubernetes.io/name: kafka-operator + app.kubernetes.io/instance: kafka-operator + app.kubernetes.io/version: "0.4.0-nightly" +subjects: + - kind: ServiceAccount + name: kafka-operator-serviceaccount + namespace: default +roleRef: + kind: ClusterRole + name: kafka-operator-clusterrole + apiGroup: rbac.authorization.k8s.io