Exemplo n.º 1
0
 def test_helper_volume_secret_manual(self):
     kdata = KDataHelper_Volume.info(base_value={
         'name': 'data-volume',
     }, value=KData_SecretManual(secretName='mycm', merge_config={
         'secret': {
             'items': [{
                 'key': 'xcmdata',
                 'path': 'xcmdata',
             }],
         },
     }), default_value={
         'persistentVolumeClaim': {
             'claimName': 'bt-storage-claim'
         }
     })
     self.assertEqual(kdata, {
         'name': 'data-volume',
         'secret': {
             'secretName': 'mycm',
             'items': [{
                 'key': 'xcmdata',
                 'path': 'xcmdata',
             }],
         }
     })
Exemplo n.º 2
0
    def define_options(self) -> Optional[Any]:
        """
        Declare the options for the Loki Stack builder.

        :return: The supported options
        """
        return {
            'basename': OptionDef(required=True, default_value='loki', allowed_types=[str]),
            'namespace': OptionDef(required=True, default_value='loki', allowed_types=[str]),
            'config': {
                'prometheus_annotation': OptionDef(required=True, default_value=False, allowed_types=[bool]),
                'loki_config': OptionDef(allowed_types=[str, ConfigFile]),
                'service_port': OptionDef(required=True, default_value=3100, allowed_types=[int]),
                'authorization': {
                    'serviceaccount_use': OptionDef(allowed_types=[str]),
                },
            },
            'container': {
                'loki': OptionDef(required=True, default_value='grafana/loki:2.0.0', allowed_types=[str]),
            },
            'kubernetes': {
                'volumes': {
                    'data': OptionDef(required=True, format=OptionDefFormat.KDATA_VOLUME,
                                      allowed_types=[Mapping, *KDataHelper_Volume.allowed_kdata()]),
                },
                'resources': {
                    'statefulset': OptionDef(allowed_types=[Mapping]),
                }
            },
        }
Exemplo n.º 3
0
 def test_helper_volume_kdata_notkdata(self):
     kdata = KDataHelper_Volume.info(base_value={
         'name': 'data-volume',
     }, value_if_kdata='not a KData', default_value={
         'persistentVolumeClaim': {
             'claimName': 'bt-storage-claim'
         }
     })
     self.assertEqual(kdata, {
         'name': 'data-volume',
         'persistentVolumeClaim': {
             'claimName': 'bt-storage-claim'
         }
     })
Exemplo n.º 4
0
 def test_helper_volume_value(self):
     kdata = KDataHelper_Volume.info(base_value={
         'name': 'data-volume',
     }, value={
         'emptyDir': {},
     }, default_value={
         'persistentVolumeClaim': {
             'claimName': 'bt-storage-claim'
         }
     })
     self.assertEqual(kdata, {
         'name': 'data-volume',
         'emptyDir': {},
     })
Exemplo n.º 5
0
 def test_helper_volume_kdata(self):
     kdata = KDataHelper_Volume.info(base_value={
         'name': 'data-volume',
     }, value_if_kdata=KData_ConfigMap(configmapName='mycm', configmapData='cmdata'), default_value={
         'persistentVolumeClaim': {
             'claimName': 'bt-storage-claim'
         }
     })
     self.assertEqual(kdata, {
         'name': 'data-volume',
         'configMap': {
             'name': 'mycm',
             'items': [{
                 'key': 'cmdata',
                 'path': 'cmdata',
             }],
         }
     })
Exemplo n.º 6
0
    def define_options(self) -> Optional[Any]:
        """
        Declare the options for the EFK builder.

        :return: The supported options
        """
        return {
            'basename': OptionDef(required=True, default_value='efk', allowed_types=[str]),
            'namespace': OptionDef(required=True, default_value='default', allowed_types=[str]),
            'config': {
                'probes': OptionDef(required=True, default_value=False, allowed_types=[bool]),
                'elasticsearch': {
                    'replicas': OptionDef(required=True, default_value=3, allowed_types=[int]),
                },
                'kibana': {
                    'service_port': OptionDef(required=True, default_value=80, allowed_types=[int]),
                },
                'authorization': {
                    'serviceaccount_create': OptionDef(required=True, default_value=True, allowed_types=[bool]),
                    'serviceaccount_use': OptionDef(allowed_types=[str]),
                    'roles_create': OptionDef(required=True, default_value=True, allowed_types=[bool]),
                    'roles_bind': OptionDef(required=True, default_value=True, allowed_types=[bool]),
                },
            },
            'enable': {
                'kibana': OptionDef(required=True, default_value=True, allowed_types=[bool]),
            },
            'container': {
                'elasticsearch': OptionDef(required=True, default_value='docker.elastic.co/elasticsearch/elasticsearch:7.9.3', allowed_types=[str]),
                'kibana': OptionDef(required=True, default_value='docker.elastic.co/kibana/kibana:7.9.3', allowed_types=[str]),
                'fluentd': OptionDef(required=True, default_value='fluent/fluentd-kubernetes-daemonset:v1.11.4-debian-elasticsearch7-1.0', allowed_types=[str]),
            },
            'kubernetes': {
                'volumes': {
                    'elasticsearch-data': OptionDef(required=True, format=OptionDefFormat.KDATA_VOLUME,
                                                    allowed_types=[Mapping, *KDataHelper_Volume.allowed_kdata()]),
                },
                'resources': {
                    'elasticsearch-statefulset': OptionDef(allowed_types=[Mapping]),
                    'kibana-deployment': OptionDef(allowed_types=[Mapping]),
                    'fluentd-daemonset': OptionDef(allowed_types=[Mapping]),
                }
            },
        }
Exemplo n.º 7
0
 def define_options(self):
     return {
         'basename':
         OptionDef(required=True, default_value='bt', allowed_types=[str]),
         'namespace':
         OptionDef(required=True, default_value='btns',
                   allowed_types=[str]),
         'config': {
             'service_port':
             OptionDef(required=True,
                       default_value=3000,
                       allowed_types=[int]),
             'frontend_url':
             OptionDef(allowed_types=[str]),
             'password':
             OptionDef(format=OptionDefFormat.KDATA_ENV,
                       allowed_types=[str, KData_Secret, KData_ConfigMap]),
             'config_file':
             OptionDef(required=True),
         },
         'container': {
             'bt': OptionDef(required=True, default_value='bt/bt:7.2.0'),
         },
         'kubernetes': {
             'volumes': {
                 'data':
                 OptionDef(required=True,
                           format=OptionDefFormat.KDATA_VOLUME,
                           default_value={'emptyDir': {}},
                           allowed_types=[
                               Mapping, *KDataHelper_Volume.allowed_kdata()
                           ]),
             },
             'resources': {
                 'deployment': OptionDef(),
             }
         },
     }
Exemplo n.º 8
0
    def define_options(self):
        """
        Declare the options for the Prometheus builder.

        :return: The supported options
        """
        return {
            'basename':
            OptionDef(required=True,
                      default_value='prometheus',
                      allowed_types=[str]),
            'namespace':
            OptionDef(required=True,
                      default_value='prometheus',
                      allowed_types=[str]),
            'config': {
                'prometheus_config':
                OptionDef(required=True, allowed_types=[str, ConfigFile]),
                'service_port':
                OptionDef(required=True,
                          default_value=9090,
                          allowed_types=[int]),
                'authorization': {
                    'serviceaccount_create':
                    OptionDef(required=True,
                              default_value=True,
                              allowed_types=[bool]),
                    'serviceaccount_use':
                    OptionDef(allowed_types=[str]),
                    'roles_create':
                    OptionDef(required=True,
                              default_value=True,
                              allowed_types=[bool]),
                    'roles_bind':
                    OptionDef(required=True,
                              default_value=True,
                              allowed_types=[bool]),
                },
            },
            'container': {
                'init-chown-data':
                OptionDef(required=True,
                          default_value='debian:9',
                          allowed_types=[str]),
                'prometheus':
                OptionDef(required=True,
                          default_value='prom/prometheus:v2.21.0',
                          allowed_types=[str]),
            },
            'kubernetes': {
                'volumes': {
                    'data':
                    OptionDef(required=True,
                              format=OptionDefFormat.KDATA_VOLUME,
                              allowed_types=[
                                  Mapping, *KDataHelper_Volume.allowed_kdata()
                              ]),
                },
                'resources': {
                    'statefulset': OptionDef(allowed_types=[Mapping]),
                }
            },
        }
Exemplo n.º 9
0
 def internal_build_service(self) -> Sequence[ObjectItem]:
     ret = []
     ret.extend([
         Object(
             {
                 'apiVersion': 'v1',
                 'kind': 'Service',
                 'metadata': {
                     'name': self.object_name('service-headless'),
                     'namespace': self.namespace(),
                 },
                 'spec': {
                     'clusterIP':
                     'None',
                     'ports': [{
                         'name': 'epmd',
                         'port': 4369,
                         'protocol': 'TCP',
                         'targetPort': 4369
                     }, {
                         'name': 'cluster-links',
                         'port': 25672,
                         'protocol': 'TCP',
                         'targetPort': 25672
                     }],
                     'selector': {
                         'app': self.object_name('pod-label-app'),
                     },
                     'type':
                     'ClusterIP',
                     'sessionAffinity':
                     'None'
                 }
             },
             name=self.BUILDITEM_SERVICE_HEADLESS,
             source=self.SOURCE_NAME,
             instance=self.basename()),
         Object(
             {
                 'apiVersion': 'apps/v1',
                 'kind': 'StatefulSet',
                 'metadata': {
                     'name': self.object_name('statefulset'),
                     'namespace': self.namespace(),
                     'labels': {
                         'app': self.object_name('pod-label-app'),
                     },
                 },
                 'spec': {
                     'selector': {
                         'matchLabels': {
                             'app': self.object_name('pod-label-app'),
                         }
                     },
                     'serviceName': self.object_name('service-headless'),
                     'replicas': 1,
                     'template': {
                         'metadata': {
                             'name':
                             self.object_name('pod-label-app'),
                             'namespace':
                             self.namespace(),
                             'labels': {
                                 'app': self.object_name('pod-label-app'),
                             },
                             'annotations':
                             ValueData(
                                 {
                                     'prometheus.io/scrape':
                                     QuotedStr('true'),
                                     'prometheus.io/path':
                                     QuotedStr('/metrics'),
                                     'prometheus.io/port':
                                     QuotedStr('15692'),
                                 },
                                 enabled=self.option_get(
                                     'config.enable_prometheus')
                                 is not False and self.option_get(
                                     'config.prometheus_annotation')
                                 is not False),
                         },
                         'spec': {
                             'initContainers': [{
                                 'name':
                                 'rabbitmq-config',
                                 'image':
                                 self.option_get('container.busybox'),
                                 'securityContext': {
                                     'runAsUser': 0,
                                     'runAsGroup': 0
                                 },
                                 'volumeMounts': [
                                     {
                                         'name': 'rabbitmq-config',
                                         'mountPath': '/tmp/rabbitmq'
                                     }, {
                                         'name': 'rabbitmq-config-rw',
                                         'mountPath': '/etc/rabbitmq'
                                     }, {
                                         'name':
                                         'rabbitmq-config-erlang-cookie',
                                         'mountPath': '/tmp/rabbitmq-cookie'
                                     }
                                 ],
                                 'command': [
                                     'sh', '-c', 'cp '
                                     '/tmp/rabbitmq/rabbitmq.conf '
                                     '/etc/rabbitmq/rabbitmq.conf '
                                     "&& echo '' "
                                     '>> '
                                     '/etc/rabbitmq/rabbitmq.conf; '
                                     'cp '
                                     '/tmp/rabbitmq/enabled_plugins '
                                     '/etc/rabbitmq/enabled_plugins; '
                                     'mkdir -p '
                                     '/var/lib/rabbitmq; '
                                     'cp '
                                     '/tmp/rabbitmq-cookie/erlang_cookie '
                                     '/var/lib/rabbitmq/.erlang.cookie; '
                                     'chmod 600 '
                                     '/var/lib/rabbitmq/.erlang.cookie; '
                                     'chown '
                                     '999.999 '
                                     '/etc/rabbitmq/rabbitmq.conf '
                                     '/etc/rabbitmq/enabled_plugins '
                                     '/var/lib/rabbitmq '
                                     '/var/lib/rabbitmq/.erlang.cookie'
                                 ]
                             }],
                             'volumes': [
                                 {
                                     'name': 'rabbitmq-config',
                                     'configMap': {
                                         'name':
                                         self.object_name('config'),
                                         'optional':
                                         False,
                                         'items': [{
                                             'key': 'enabled_plugins',
                                             'path': 'enabled_plugins'
                                         }, {
                                             'key': 'rabbitmq.conf',
                                             'path': 'rabbitmq.conf'
                                         }]
                                     }
                                 },
                                 {
                                     'name': 'rabbitmq-config-rw',
                                     'emptyDir': {}
                                 },
                                 KDataHelper_Volume.info(
                                     base_value={
                                         'name':
                                         'rabbitmq-config-erlang-cookie',
                                     },
                                     value_if_kdata=self.option_get(
                                         'config.erlang_cookie'),
                                     default_value={
                                         'secret': {
                                             'secretName':
                                             self.object_name(
                                                 'config-secret'),
                                             'items': [{
                                                 'key':
                                                 'erlang_cookie',
                                                 'path':
                                                 'erlang_cookie',
                                             }]
                                         },
                                     },
                                     key_path='erlang_cookie'),
                                 KDataHelper_Volume.info(
                                     base_value={
                                         'name':
                                         'rabbitmq-config-load-definition',
                                     },
                                     value_if_kdata=self.option_get(
                                         'config.load_definitions'),
                                     default_value={
                                         'secret': {
                                             'secretName':
                                             self.object_name(
                                                 'config-secret'),
                                             'items': [{
                                                 'key':
                                                 'load_definition.json',
                                                 'path':
                                                 'load_definition.json',
                                             }]
                                         }
                                     },
                                     key_path='load_definition.json',
                                     enabled=self.option_get(
                                         'config.load_definitions')
                                     is not None),
                                 KDataHelper_Volume.info(
                                     base_value={
                                         'name': 'rabbitmq-data',
                                     },
                                     value=self.option_get(
                                         'kubernetes.volumes.data')),
                             ],
                             'serviceAccountName':
                             ValueData(
                                 value=self.object_name('service-account'),
                                 enabled=self.object_name('service-account')
                                 is not None),
                             'securityContext': {
                                 'fsGroup': 999,
                                 'runAsUser': 999,
                                 'runAsGroup': 999
                             },
                             'containers': [{
                                 'name':
                                 'rabbitmq',
                                 'image':
                                 self.option_get('container.rabbitmq'),
                                 'volumeMounts': [
                                     {
                                         'name': 'rabbitmq-config-rw',
                                         'mountPath': '/etc/rabbitmq'
                                     }, {
                                         'name': 'rabbitmq-data',
                                         'mountPath':
                                         '/var/lib/rabbitmq/mnesia'
                                     },
                                     ValueData(value={
                                         'name':
                                         'rabbitmq-config-load-definition',
                                         'mountPath':
                                         '/etc/rabbitmq-load-definition',
                                         'readOnly': True,
                                     },
                                               enabled=self.option_get(
                                                   'config.load_definitions'
                                               ) is not None)
                                 ],
                                 'ports': [
                                     {
                                         'name': 'amqp',
                                         'containerPort': 5672,
                                         'protocol': 'TCP'
                                     }, {
                                         'name': 'management',
                                         'containerPort': 15672,
                                         'protocol': 'TCP'
                                     },
                                     ValueData(
                                         value={
                                             'name': 'prometheus',
                                             'containerPort': 15692,
                                             'protocol': 'TCP'
                                         },
                                         enabled=self.option_get(
                                             'config.enable_prometheus')
                                         is not False), {
                                             'name': 'epmd',
                                             'containerPort': 4369,
                                             'protocol': 'TCP'
                                         }
                                 ],
                                 'livenessProbe': {
                                     'exec': {
                                         'command':
                                         ['rabbitmq-diagnostics', 'status']
                                     },
                                     'initialDelaySeconds': 60,
                                     'periodSeconds': 60,
                                     'timeoutSeconds': 15
                                 },
                                 'readinessProbe': {
                                     'exec': {
                                         'command':
                                         ['rabbitmq-diagnostics', 'ping']
                                     },
                                     'initialDelaySeconds': 20,
                                     'periodSeconds': 60,
                                     'timeoutSeconds': 10
                                 },
                                 'resources':
                                 ValueData(value=self.option_get(
                                     'kubernetes.resources.statefulset'),
                                           disabled_if_none=True),
                             }]
                         }
                     }
                 }
             },
             name=self.BUILDITEM_STATEFULSET,
             source=self.SOURCE_NAME,
             instance=self.basename()),
         Object(
             {
                 'kind': 'Service',
                 'apiVersion': 'v1',
                 'metadata': {
                     'name': self.object_name('service'),
                     'namespace': self.namespace(),
                     'labels': {
                         'app': self.object_name('pod-label-app')
                     },
                 },
                 'spec': {
                     'type':
                     'ClusterIP',
                     'ports': [{
                         'name': 'http',
                         'protocol': 'TCP',
                         'port': 15672,
                     },
                               ValueData(value={
                                   'name': 'prometheus',
                                   'protocol': 'TCP',
                                   'port': 15692
                               },
                                         enabled=self.option_get(
                                             'config.enable_prometheus')
                                         is not False), {
                                             'name': 'amqp',
                                             'protocol': 'TCP',
                                             'port': 5672
                                         }],
                     'selector': {
                         'app': self.object_name('pod-label-app')
                     }
                 }
             },
             name=self.BUILDITEM_SERVICE,
             source=self.SOURCE_NAME,
             instance=self.basename())
     ])
     return ret
Exemplo n.º 10
0
    def internal_build_service(self) -> Sequence[ObjectItem]:
        self._checkdownloaded()

        ret = []

        if self._downloadedfiles is not None:
            for item in self._downloadedfiles['headless-service.yaml']:
                ritem = item
                if ritem['kind'] == 'Service':
                    ritem = Object(jsonpatchext.apply_patch(ritem, [
                        {
                            'op': 'check',
                            'path': '/metadata/name',
                            'cmp': 'equals',
                            'value': 'rabbitmq-headless'
                        },
                        {
                            'op': 'check',
                            'path': '/metadata/namespace',
                            'cmp': 'equals',
                            'value': 'test-rabbitmq'
                        },
                        {
                            'op': 'replace',
                            'path': '/metadata/name',
                            'value': self.object_name('service-headless')
                        },
                        {
                            'op': 'replace',
                            'path': '/metadata/namespace',
                            'value': self.namespace()
                        },
                        {
                            'op': 'replace',
                            'path': '/spec/selector/app',
                            'value': self.object_name('pod-label-app')
                        },
                    ],
                                                            in_place=False),
                                   name=self.BUILDITEM_SERVICE_HEADLESS,
                                   source=self.SOURCE_NAME,
                                   instance=self.basename())
                ret.append(ritem)

            for item in self._downloadedfiles['statefulset.yaml']:
                ritem = item
                if ritem['kind'] == 'StatefulSet':
                    ritempatch = [
                        {
                            'op': 'check',
                            'path': '/metadata/name',
                            'cmp': 'equals',
                            'value': 'rabbitmq'
                        },
                        {
                            'op': 'check',
                            'path': '/metadata/namespace',
                            'cmp': 'equals',
                            'value': 'test-rabbitmq'
                        },
                        {
                            'op': 'check',
                            'path':
                            '/spec/template/spec/initContainers/0/image',
                            'cmp': 'startswith',
                            'value': 'busybox'
                        },
                        {
                            'op': 'check',
                            'path': '/spec/template/spec/volumes/2/name',
                            'cmp': 'equals',
                            'value': 'rabbitmq-data'
                        },
                        {
                            'op': 'check',
                            'path': '/spec/template/spec/containers/0/image',
                            'cmp': 'startswith',
                            'value': 'rabbitmq'
                        },
                        {
                            'op': 'check',
                            'path':
                            '/spec/template/spec/containers/0/env/0/name',
                            'cmp': 'equals',
                            'value': 'RABBITMQ_DEFAULT_PASS'
                        },
                        {
                            'op': 'check',
                            'path':
                            '/spec/template/spec/containers/0/env/1/name',
                            'cmp': 'equals',
                            'value': 'RABBITMQ_DEFAULT_USER'
                        },
                        {
                            'op': 'check',
                            'path':
                            '/spec/template/spec/containers/0/env/2/name',
                            'cmp': 'equals',
                            'value': 'RABBITMQ_ERLANG_COOKIE'
                        },
                        {
                            'op': 'check',
                            'path':
                            '/spec/template/spec/containers/0/ports/2/name',
                            'cmp': 'equals',
                            'value': 'prometheus'
                        },
                        {
                            'op': 'replace',
                            'path': '/metadata/name',
                            'value': self.object_name('statefulset')
                        },
                        {
                            'op': 'replace',
                            'path': '/metadata/namespace',
                            'value': self.namespace()
                        },
                        {
                            'op': 'merge',
                            'path': '/metadata',
                            'value': {
                                'labels': {}
                            }
                        },
                        {
                            'op': 'merge',
                            'path': '/metadata/labels',
                            'value': {
                                'app': self.object_name('pod-label-app')
                            }
                        },
                        {
                            'op': 'replace',
                            'path': '/spec/selector/matchLabels/app',
                            'value': self.object_name('pod-label-app')
                        },
                        {
                            'op': 'replace',
                            'path': '/spec/serviceName',
                            'value': self.object_name('service-headless')
                        },
                        {
                            'op': 'remove',
                            'path': '/spec/volumeClaimTemplates'
                        },
                        {
                            'op': 'replace',
                            'path': '/spec/template/metadata/name',
                            'value': self.object_name('pod-label-app')
                        },
                        {
                            'op': 'replace',
                            'path': '/spec/template/metadata/namespace',
                            'value': self.namespace()
                        },
                        {
                            'op': 'replace',
                            'path': '/spec/template/metadata/labels/app',
                            'value': self.object_name('pod-label-app')
                        },
                        {
                            'op':
                            'replace',
                            'path':
                            '/spec/template/spec/serviceAccount',
                            'value':
                            ValueData(
                                value=self.object_name('service-account'),
                                enabled=self.object_name('service-account')
                                is not None)
                        },
                        {
                            'op':
                            'replace',
                            'path':
                            '/spec/template/spec/volumes/2',
                            'value':
                            KDataHelper_Volume.info(
                                base_value={
                                    'name': 'rabbitmq-data',
                                },
                                value=self.option_get(
                                    'kubernetes.volumes.data'))
                        },
                        {
                            'op':
                            'replace',
                            'path':
                            '/spec/template/spec/containers/0/env/0',
                            'value':
                            KDataHelper_Env.info(
                                base_value={'name': 'RABBITMQ_DEFAULT_PASS'},
                                value=self.option_get('config.admin.password'),
                                default_value={
                                    'valueFrom': {
                                        'secretKeyRef': {
                                            'name':
                                            self.object_name('config-secret'),
                                            'key':
                                            'admin.password'
                                        }
                                    },
                                })
                        },
                        {
                            'op':
                            'replace',
                            'path':
                            '/spec/template/spec/containers/0/env/1',
                            'value':
                            KDataHelper_Env.info(
                                base_value={'name': 'RABBITMQ_DEFAULT_USER'},
                                value=self.option_get('config.admin.username'),
                                default_value={
                                    'valueFrom': {
                                        'secretKeyRef': {
                                            'name':
                                            self.object_name('config-secret'),
                                            'key':
                                            'admin.username'
                                        }
                                    },
                                })
                        },
                        {
                            'op':
                            'replace',
                            'path':
                            '/spec/template/spec/containers/0/env/2',
                            'value':
                            KDataHelper_Env.info(
                                base_value={'name': 'RABBITMQ_ERLANG_COOKIE'},
                                value=self.option_get('config.erlang_cookie'),
                                default_value={
                                    'valueFrom': {
                                        'secretKeyRef': {
                                            'name':
                                            self.object_name('config-secret'),
                                            'key':
                                            'erlang_cookie'
                                        }
                                    },
                                })
                        },
                        {
                            'op':
                            'add',
                            'path':
                            '/spec/template/spec/containers/0/resources',
                            'value':
                            ValueData(value=self.option_get(
                                'kubernetes.resources.statefulset'),
                                      disabled_if_none=True),
                        },
                    ]

                    if self.option_get('container.busybox') is not None:
                        ritempatch.append({
                            'op':
                            'replace',
                            'path':
                            '/spec/template/spec/initContainers/0/image',
                            'value':
                            self.option_get('container.busybox')
                        })
                    if self.option_get('container.rabbitmq') is not None:
                        ritempatch.append({
                            'op':
                            'replace',
                            'path':
                            '/spec/template/spec/containers/0/image',
                            'value':
                            self.option_get('container.rabbitmq')
                        })
                    if self.option_get('config.enable_prometheus') is False:
                        ritempatch.append({
                            'op':
                            'remove',
                            'path':
                            '/spec/template/spec/containers/0/ports/2'
                        })
                    if self.option_get(
                            'config.enable_prometheus'
                    ) is not False and self.option_get(
                            'config.prometheus_annotation') is not False:
                        ritempatch.append({
                            'op': 'merge',
                            'path': '/spec/template/metadata',
                            'value': {
                                'annotations': {
                                    'prometheus.io/scrape': QuotedStr('true'),
                                    'prometheus.io/path':
                                    QuotedStr('/metrics'),
                                    'prometheus.io/port': QuotedStr('15692'),
                                }
                            }
                        })
                    if self.option_get('config.load_definitions') is not None:
                        ritempatch.append({
                            'op':
                            'add',
                            'path':
                            '/spec/template/spec/volumes',
                            'value':
                            KDataHelper_Volume.info(
                                base_value={
                                    'name': 'rabbitmq-config-load-definition',
                                },
                                value_if_kdata=self.option_get(
                                    'config.load_definitions'),
                                default_value={
                                    'secret': {
                                        'secretName':
                                        self.object_name('config-secret'),
                                        'items': [{
                                            'key':
                                            'load_definition.json',
                                            'path':
                                            'load_definition.json',
                                        }]
                                    }
                                },
                                key_path='load_definition.json')
                        })
                        ritempatch.append({
                            'op': 'add',
                            'path':
                            '/spec/template/spec/containers/0/volumeMounts',
                            'value': {
                                'name': 'rabbitmq-config-load-definition',
                                'mountPath': '/etc/rabbitmq-load-definition',
                                'readOnly': True,
                            }
                        })

                    ritem = Object(jsonpatchext.apply_patch(ritem,
                                                            ritempatch,
                                                            in_place=False),
                                   name=self.BUILDITEM_STATEFULSET,
                                   source=self.SOURCE_NAME,
                                   instance=self.basename())
                ret.append(ritem)

            for item in self._downloadedfiles['client-service.yaml']:
                ritem = item
                if ritem['kind'] == 'Service':
                    ritempatch = [
                        {
                            'op': 'check',
                            'path': '/metadata/name',
                            'cmp': 'equals',
                            'value': 'rabbitmq-client'
                        },
                        {
                            'op': 'check',
                            'path': '/metadata/namespace',
                            'cmp': 'equals',
                            'value': 'test-rabbitmq'
                        },
                        {
                            'op': 'check',
                            'path': '/spec/ports/1/name',
                            'cmp': 'equals',
                            'value': 'prometheus'
                        },
                        {
                            'op': 'replace',
                            'path': '/metadata/name',
                            'value': self.object_name('service')
                        },
                        {
                            'op': 'replace',
                            'path': '/metadata/namespace',
                            'value': self.namespace()
                        },
                        {
                            'op': 'replace',
                            'path': '/metadata/labels/app',
                            'value': self.object_name('pod-label-app')
                        },
                        {
                            'op': 'replace',
                            'path': '/spec/type',
                            'value': self.option_get('config.servicetype')
                        },
                        {
                            'op': 'replace',
                            'path': '/spec/selector/app',
                            'value': self.object_name('pod-label-app')
                        },
                    ]
                    if self.option_get('config.enable_prometheus') is False:
                        ritempatch.append({
                            'op': 'remove',
                            'path': '/spec/ports/1'
                        })
                    ritem = Object(jsonpatchext.apply_patch(ritem,
                                                            ritempatch,
                                                            in_place=False),
                                   name=self.BUILDITEM_SERVICE,
                                   source=self.SOURCE_NAME,
                                   instance=self.basename())
                ret.append(ritem)

        self._check_object_must_have(
            ret, [
                self.BUILDITEM_SERVICE_HEADLESS, self.BUILDITEM_STATEFULSET,
                self.BUILDITEM_SERVICE
            ], 'headless-service.yaml, statefulset.yaml, client-service.yaml')

        return ret
Exemplo n.º 11
0
    def internal_build_service(self) -> Sequence[ObjectItem]:
        ret = []

        ret.extend([
            Object(
                {
                    'apiVersion': 'v1',
                    'kind': 'Service',
                    'metadata': {
                        'name': self.object_name('service-headless'),
                        'namespace': self.namespace(),
                        'labels': {
                            'app': self.object_name('pod-label-app'),
                        }
                    },
                    'spec': {
                        'clusterIP':
                        'None',
                        'ports':
                        [{
                            'port': self.option_get('config.service_port'),
                            'protocol': 'TCP',
                            'name': 'http-metrics',
                            'targetPort': 'http-metrics'
                        }],
                        'selector': {
                            'app': self.object_name('pod-label-app'),
                        }
                    }
                },
                name=self.BUILDITEM_SERVICE_HEADLESS,
                source=self.SOURCE_NAME,
                instance=self.basename()),
            Object(
                {
                    'apiVersion': 'v1',
                    'kind': 'Service',
                    'metadata': {
                        'name': self.object_name('service'),
                        'namespace': self.namespace(),
                        'labels': {
                            'app': self.object_name('pod-label-app'),
                        },
                    },
                    'spec': {
                        'type':
                        'ClusterIP',
                        'ports': [{
                            'port':
                            self.option_get('config.service_port'),
                            'protocol':
                            'TCP',
                            'name':
                            'http-metrics',
                            'targetPort':
                            'http-metrics'
                        }],
                        'selector': {
                            'app': self.object_name('pod-label-app'),
                        },
                    }
                },
                name=self.BUILDITEM_SERVICE,
                source=self.SOURCE_NAME,
                instance=self.basename()),
            Object(
                {
                    'apiVersion': 'apps/v1',
                    'kind': 'StatefulSet',
                    'metadata': {
                        'name': self.object_name('statefulset'),
                        'namespace': self.namespace(),
                        'labels': {
                            'app': self.object_name('pod-label-app'),
                        },
                    },
                    'spec': {
                        'podManagementPolicy': 'OrderedReady',
                        'replicas': 1,
                        'selector': {
                            'matchLabels': {
                                'app': self.object_name('pod-label-app'),
                            }
                        },
                        'serviceName': self.object_name('service-headless'),
                        'updateStrategy': {
                            'type': 'RollingUpdate'
                        },
                        'template': {
                            'metadata': {
                                'labels': {
                                    'app': self.object_name('pod-label-app'),
                                },
                                'annotations':
                                ValueData(
                                    {
                                        'prometheus.io/scrape':
                                        QuotedStr('true'),
                                        'prometheus.io/port':
                                        QuotedStr('http-metrics'),
                                    },
                                    enabled=self.option_get(
                                        'config.prometheus_annotation')
                                    is not False),
                            },
                            'spec': {
                                'serviceAccountName':
                                ValueData(self.option_get(
                                    'config.authorization.serviceaccount_use'),
                                          disabled_if_none=True),
                                'securityContext': {
                                    'fsGroup': 10001,
                                    'runAsGroup': 10001,
                                    'runAsNonRoot': True,
                                    'runAsUser': 10001
                                },
                                'containers': [{
                                    'name':
                                    'loki',
                                    'image':
                                    self.option_get('container.loki'),
                                    'args':
                                    ['-config.file=/etc/loki/loki.yaml'],
                                    'volumeMounts': [{
                                        'name': 'config',
                                        'mountPath': '/etc/loki'
                                    }, {
                                        'name': 'storage',
                                        'mountPath': '/data',
                                        'subPath': None
                                    }],
                                    'ports': [{
                                        'name': 'http-metrics',
                                        'containerPort': 3100,
                                        'protocol': 'TCP'
                                    }],
                                    'livenessProbe': {
                                        'httpGet': {
                                            'path': '/ready',
                                            'port': 'http-metrics'
                                        },
                                        'initialDelaySeconds': 45
                                    },
                                    'readinessProbe': {
                                        'httpGet': {
                                            'path': '/ready',
                                            'port': 'http-metrics'
                                        },
                                        'initialDelaySeconds': 45
                                    },
                                    'securityContext': {
                                        'readOnlyRootFilesystem': True
                                    },
                                    'resources':
                                    ValueData(value=self.option_get(
                                        'kubernetes.resources.statefulset'),
                                              disabled_if_none=True),
                                }],
                                'terminationGracePeriodSeconds':
                                4800,
                                'volumes': [{
                                    'name': 'config',
                                    'secret': {
                                        'secretName':
                                        self.object_name('config-secret'),
                                        'items': [{
                                            'key': 'loki.yaml',
                                            'path': 'loki.yaml',
                                        }]
                                    }
                                },
                                            KDataHelper_Volume.info(
                                                base_value={
                                                    'name': 'storage',
                                                },
                                                value=self.option_get(
                                                    'kubernetes.volumes.data'))
                                            ]
                            }
                        }
                    }
                },
                name=self.BUILDITEM_STATEFULSET,
                source=self.SOURCE_NAME,
                instance=self.basename()),
        ])

        return ret
Exemplo n.º 12
0
    def define_options(self):
        """
        Declare the options for the RabbitMQ Online builder.

        :return: The supported options
        """
        return {
            'basename':
            OptionDef(required=True,
                      default_value='rabbitmq',
                      allowed_types=[str]),
            'namespace':
            OptionDef(required=True,
                      default_value='rabbitmq',
                      allowed_types=[str]),
            'config': {
                'github':
                OptionDef(required=True,
                          default_value='rabbitmq/diy-kubernetes-examples',
                          allowed_types=[str]),
                'github_commit':
                OptionDef(required=True,
                          default_value='master',
                          allowed_types=[str]),
                'enabled_plugins':
                OptionDef(default_value=['rabbitmq_peer_discovery_k8s'],
                          allowed_types=[Sequence]),
                'rabbitmq_conf':
                OptionDef(allowed_types=[str, ConfigFile]),
                'admin': {
                    'username':
                    OptionDef(
                        required=True,
                        default_value='admin',
                        format=OptionDefFormat.KDATA_ENV,
                        allowed_types=[str, *KDataHelper_Env.allowed_kdata()]),
                    'password':
                    OptionDef(required=True,
                              format=OptionDefFormat.KDATA_ENV,
                              allowed_types=[str, KData_Secret]),
                },
                'erlang_cookie':
                OptionDef(required=True,
                          default_value=str(uuid.uuid4()),
                          format=OptionDefFormat.KDATA_VOLUME,
                          allowed_types=[str, KData_Secret]),
                'loglevel':
                OptionDef(required=True,
                          default_value='info',
                          allowed_types=[str]),
                'enable_prometheus':
                OptionDef(required=True,
                          default_value=True,
                          allowed_types=[bool]),
                'prometheus_annotation':
                OptionDef(required=True,
                          default_value=False,
                          allowed_types=[bool]),
                'load_definitions':
                OptionDef(format=OptionDefFormat.KDATA_VOLUME,
                          allowed_types=[str, KData_Secret]),
                'servicetype':
                OptionDef(required=True,
                          default_value='LoadBalancer',
                          allowed_types=[str]),
                'authorization': {
                    'serviceaccount_create':
                    OptionDef(required=True,
                              default_value=True,
                              allowed_types=[bool]),
                    'serviceaccount_use':
                    OptionDef(allowed_types=[str]),
                    'roles_create':
                    OptionDef(required=True,
                              default_value=True,
                              allowed_types=[bool]),
                    'roles_bind':
                    OptionDef(required=True,
                              default_value=True,
                              allowed_types=[bool]),
                },
            },
            'container': {
                'busybox': OptionDef(allowed_types=[str]),
                'rabbitmq': OptionDef(allowed_types=[str]),
            },
            'kubernetes': {
                'volumes': {
                    'data':
                    OptionDef(required=True,
                              format=OptionDefFormat.KDATA_VOLUME,
                              allowed_types=[
                                  Mapping,
                                  KDataHelper_Volume.allowed_kdata()
                              ]),
                },
                'resources': {
                    'statefulset': OptionDef(allowed_types=[Mapping]),
                }
            },
        }
Exemplo n.º 13
0
    def internal_build_service(self) -> Sequence[ObjectItem]:
        ret = []

        ret.extend([
            Object(
                {
                    'kind': 'Service',
                    'apiVersion': 'v1',
                    'metadata': {
                        'name': self.object_name('elasticsearch-service'),
                        'namespace': self.namespace(),
                        'labels': {
                            'app':
                            self.object_name('elasticsearch-pod-label-app'),
                        }
                    },
                    'spec': {
                        'selector': {
                            'app':
                            self.object_name('elasticsearch-pod-label-app'),
                        },
                        'clusterIP':
                        'None',
                        'ports': [{
                            'port': 9200,
                            'name': 'rest'
                        }, {
                            'port': 9300,
                            'name': 'inter-node'
                        }],
                    }
                },
                name=self.BUILDITEM_ELASTICSEARCH_SERVICE,
                source=self.SOURCE_NAME,
                instance=self.basename()),
            Object(
                {
                    'apiVersion': 'apps/v1',
                    'kind': 'StatefulSet',
                    'metadata': {
                        'name': self.object_name('elasticsearch-statefulset'),
                        'namespace': self.namespace(),
                    },
                    'spec': {
                        'serviceName':
                        self.object_name('elasticsearch-service'),
                        'replicas':
                        self.option_get('config.elasticsearch.replicas'),
                        'selector': {
                            'matchLabels': {
                                'app':
                                self.object_name(
                                    'elasticsearch-pod-label-app'),
                            }
                        },
                        'template': {
                            'metadata': {
                                'labels': {
                                    'app':
                                    self.object_name(
                                        'elasticsearch-pod-label-app'),
                                }
                            },
                            'spec': {
                                'volumes': [
                                    KDataHelper_Volume.info(
                                        base_value={
                                            'name': 'data',
                                        },
                                        value=self.option_get(
                                            'kubernetes.volumes.elasticsearch-data'
                                        )),
                                ],
                                'containers': [{
                                    'name':
                                    'elasticsearch',
                                    'image':
                                    self.option_get('container.elasticsearch'),
                                    'ports': [{
                                        'containerPort': 9200,
                                        'name': 'rest',
                                        'protocol': 'TCP'
                                    }, {
                                        'containerPort': 9300,
                                        'name': 'inter-node',
                                        'protocol': 'TCP'
                                    }],
                                    'volumeMounts': [{
                                        'name':
                                        'data',
                                        'mountPath':
                                        '/usr/share/elasticsearch/data'
                                    }],
                                    'env': [{
                                        'name':
                                        'cluster.name',
                                        'value':
                                        self.object_name(
                                            'elasticsearch-statefulset'),
                                    }, {
                                        'name': 'NODE_NAME',
                                        'valueFrom': {
                                            'fieldRef': {
                                                'fieldPath': 'metadata.name'
                                            }
                                        },
                                    }, {
                                        'name':
                                        'node.name',
                                        'value':
                                        QuotedStr('$(NODE_NAME).{}'.format(
                                            self.object_name(
                                                'elasticsearch-service'))),
                                    }, {
                                        'name':
                                        'discovery.seed_hosts',
                                        'value':
                                        ','.join([
                                            '{}-{}.{}'.format(
                                                self.object_name(
                                                    'elasticsearch-statefulset'
                                                ), rpl,
                                                self.object_name(
                                                    'elasticsearch-service'))
                                            for rpl in range(
                                                self.option_get(
                                                    'config.elasticsearch.replicas'
                                                ))
                                        ]),
                                    }, {
                                        'name':
                                        'cluster.initial_master_nodes',
                                        'value':
                                        ','.join([
                                            '{}-{}.{}'.format(
                                                self.object_name(
                                                    'elasticsearch-statefulset'
                                                ), rpl,
                                                self.object_name(
                                                    'elasticsearch-service'))
                                            for rpl in range(
                                                self.option_get(
                                                    'config.elasticsearch.replicas'
                                                ))
                                        ]),
                                    }, {
                                        'name': 'ES_JAVA_OPTS',
                                        'value': '-Xms512m '
                                        '-Xmx512m'
                                    }],
                                    'resources':
                                    ValueData(value=self.option_get(
                                        'kubernetes.resources.elasticsearch-statefulset'
                                    ),
                                              disabled_if_none=True),
                                }],
                                'initContainers': [{
                                    'name':
                                    'fix-permissions',
                                    'image':
                                    'busybox',
                                    'command': [
                                        'sh', '-c', 'chown -R '
                                        '1000:1000 '
                                        '/usr/share/elasticsearch/data'
                                    ],
                                    'securityContext': {
                                        'privileged': True
                                    },
                                    'volumeMounts': [{
                                        'name':
                                        'data',
                                        'mountPath':
                                        '/usr/share/elasticsearch/data'
                                    }],
                                }, {
                                    'name':
                                    'increase-vm-max-map',
                                    'image':
                                    'busybox',
                                    'command': [
                                        'sysctl', '-w',
                                        'vm.max_map_count=262144'
                                    ],
                                    'securityContext': {
                                        'privileged': True
                                    },
                                }, {
                                    'name':
                                    'increase-fd-ulimit',
                                    'image':
                                    'busybox',
                                    'command':
                                    ['sh', '-c', 'ulimit -n '
                                     '65536'],
                                    'securityContext': {
                                        'privileged': True
                                    },
                                }]
                            }
                        },
                    }
                },
                name=self.BUILDITEM_ELASTICSEARCH_STATEFULSET,
                source=self.SOURCE_NAME,
                instance=self.basename()),
            Object(
                {
                    'apiVersion': 'apps/v1',
                    'kind': 'DaemonSet',
                    'metadata': {
                        'name': self.object_name('fluentd-daemonset'),
                        'namespace': self.namespace(),
                        'labels': {
                            'app': self.object_name('fluentd-pod-label-app'),
                        }
                    },
                    'spec': {
                        'selector': {
                            'matchLabels': {
                                'app':
                                self.object_name('fluentd-pod-label-app'),
                            }
                        },
                        'template': {
                            'metadata': {
                                'labels': {
                                    'app':
                                    self.object_name('fluentd-pod-label-app'),
                                }
                            },
                            'spec': {
                                'serviceAccount':
                                self.object_name('service-account'),
                                'serviceAccountName':
                                self.object_name('service-account'),
                                'tolerations': [{
                                    'key': 'node-role.kubernetes.io/master',
                                    'effect': 'NoSchedule'
                                }],
                                'containers': [{
                                    'name':
                                    'fluentd',
                                    'image':
                                    self.option_get('container.fluentd'),
                                    'env': [
                                        {
                                            'name':
                                            'FLUENT_ELASTICSEARCH_HOST',
                                            'value':
                                            '{}.{}.svc.cluster.local'.format(
                                                self.object_name(
                                                    'elasticsearch-service'),
                                                self.namespace()),
                                        }, {
                                            'name':
                                            'FLUENT_ELASTICSEARCH_PORT',
                                            'value': '9200'
                                        }, {
                                            'name':
                                            'FLUENT_ELASTICSEARCH_SCHEME',
                                            'value': 'http'
                                        }, {
                                            'name': 'FLUENTD_SYSTEMD_CONF',
                                            'value': 'disable'
                                        },
                                        ValueData(value={
                                            'name':
                                            'FLUENT_CONTAINER_TAIL_PARSER_TYPE',
                                            'value':
                                            '/^(?<time>.+) (?<stream>stdout|stderr) [^ ]* (?<log>.*)$/',
                                        },
                                                  enabled=self.kubragen.
                                                  provider.provider
                                                  == PROVIDER_K3D
                                                  or self.kubragen.provider.
                                                  provider == PROVIDER_K3S)
                                    ],
                                    'volumeMounts': [{
                                        'name': 'varlog',
                                        'mountPath': '/var/log'
                                    }, {
                                        'name': 'varlibdockercontainers',
                                        'mountPath':
                                        '/var/lib/docker/containers',
                                        'readOnly': True
                                    }],
                                    'resources':
                                    ValueData(value=self.option_get(
                                        'kubernetes.resources.fluentd-daemonset'
                                    ),
                                              disabled_if_none=True),
                                }],
                                'terminationGracePeriodSeconds':
                                30,
                                'volumes': [{
                                    'name': 'varlog',
                                    'hostPath': {
                                        'path': '/var/log'
                                    }
                                }, {
                                    'name': 'varlibdockercontainers',
                                    'hostPath': {
                                        'path': '/var/lib/docker/containers'
                                    }
                                }]
                            }
                        }
                    }
                },
                name=self.BUILDITEM_FLUENTD_DAEMONSET,
                source=self.SOURCE_NAME,
                instance=self.basename()),
        ])

        if self.option_get('enable.kibana'):
            ret.extend([
                Object(
                    {
                        'apiVersion': 'v1',
                        'kind': 'Service',
                        'metadata': {
                            'name': self.object_name('kibana-service'),
                            'namespace': self.namespace(),
                            'labels': {
                                'app':
                                self.object_name('kibana-pod-label-app'),
                            },
                        },
                        'spec': {
                            'ports': [{
                                'port':
                                self.option_get('config.kibana.service_port'),
                                'targetPort':
                                5601,
                            }],
                            'selector': {
                                'app':
                                self.object_name('kibana-pod-label-app'),
                            }
                        }
                    },
                    name=self.BUILDITEM_KIBANA_SERVICE,
                    source=self.SOURCE_NAME,
                    instance=self.basename()),
                Object(
                    {
                        'apiVersion': 'apps/v1',
                        'kind': 'Deployment',
                        'metadata': {
                            'name': self.object_name('kibana-deployment'),
                            'namespace': self.namespace(),
                            'labels': {
                                'app':
                                self.object_name('kibana-pod-label-app'),
                            }
                        },
                        'spec': {
                            # 'replicas': 1,
                            'selector': {
                                'matchLabels': {
                                    'app':
                                    self.object_name('kibana-pod-label-app'),
                                }
                            },
                            'template': {
                                'metadata': {
                                    'labels': {
                                        'app':
                                        self.object_name(
                                            'kibana-pod-label-app'),
                                    }
                                },
                                'spec': {
                                    'containers': [{
                                        'name':
                                        'kibana',
                                        'image':
                                        self.option_get('container.kibana'),
                                        'env': [{
                                            'name':
                                            'ELASTICSEARCH_HOSTS',
                                            'value':
                                            'http://{}:9200'.format(
                                                self.object_name(
                                                    'elasticsearch-service')),
                                        }],
                                        'ports': [{
                                            'containerPort': 5601
                                        }],
                                        'livenessProbe':
                                        ValueData(value={
                                            'httpGet': {
                                                'path': '/api/status',
                                                'port': 5601,
                                            },
                                            'initialDelaySeconds': 30,
                                            'timeoutSeconds': 20,
                                        },
                                                  enabled=self.option_get(
                                                      'config.probes')),
                                        'readinessProbe':
                                        ValueData(value={
                                            'httpGet': {
                                                'path': '/api/status',
                                                'port': 5601,
                                            },
                                            'initialDelaySeconds': 30,
                                            'timeoutSeconds': 20,
                                        },
                                                  enabled=self.option_get(
                                                      'config.probes')),
                                        'resources':
                                        ValueData(value=self.option_get(
                                            'kubernetes.resources.kibana-deployment'
                                        ),
                                                  disabled_if_none=True),
                                    }]
                                }
                            }
                        }
                    },
                    name=self.BUILDITEM_KIBANA_DEPLOYMENT,
                    source=self.SOURCE_NAME,
                    instance=self.basename()),
            ])

        return ret
Exemplo n.º 14
0
    def define_options(self) -> Optional[Any]:
        """
        Declare the options for the RabbitMQ builder.

        :return: The supported options
        """
        return {
            'basename':
            OptionDef(required=True,
                      default_value='rabbitmq',
                      allowed_types=[str]),
            'namespace':
            OptionDef(required=True,
                      default_value='rabbitmq',
                      allowed_types=[str]),
            'config': {
                'enabled_plugins':
                OptionDef(default_value=['rabbitmq_peer_discovery_k8s'],
                          allowed_types=[Sequence]),
                'rabbitmq_conf':
                OptionDef(allowed_types=[str, ConfigFile]),
                'erlang_cookie':
                OptionDef(required=True,
                          default_value=str(uuid.uuid4()),
                          format=OptionDefFormat.KDATA_VOLUME,
                          allowed_types=[str, dict, KData_Secret]),
                'loglevel':
                OptionDef(required=True,
                          default_value='info',
                          allowed_types=[str]),
                'enable_prometheus':
                OptionDef(required=True,
                          default_value=True,
                          allowed_types=[bool]),
                'prometheus_annotation':
                OptionDef(required=True,
                          default_value=False,
                          allowed_types=[bool]),
                'load_definitions':
                OptionDef(format=OptionDefFormat.KDATA_VOLUME,
                          allowed_types=[str, KData_Secret]),
                'authorization': {
                    'serviceaccount_create':
                    OptionDef(required=True,
                              default_value=True,
                              allowed_types=[bool]),
                    'serviceaccount_use':
                    OptionDef(allowed_types=[str]),
                    'roles_create':
                    OptionDef(required=True,
                              default_value=True,
                              allowed_types=[bool]),
                    'roles_bind':
                    OptionDef(required=True,
                              default_value=True,
                              allowed_types=[bool]),
                },
            },
            'container': {
                'busybox':
                OptionDef(required=True,
                          default_value='busybox:1.32.0',
                          allowed_types=[str]),
                'rabbitmq':
                OptionDef(required=True,
                          default_value='rabbitmq:3.8.9-alpine',
                          allowed_types=[str]),
            },
            'kubernetes': {
                'volumes': {
                    'data':
                    OptionDef(required=True,
                              format=OptionDefFormat.KDATA_VOLUME,
                              allowed_types=[
                                  dict, *KDataHelper_Volume.allowed_kdata()
                              ]),
                },
                'resources': {
                    'statefulset': OptionDef(allowed_types=[dict]),
                }
            },
        }