Esta guía describe cómo configurar los clústeres de ClickHouse y Keeper mediante el operador.
Configuración de ClickHouseCluster
Configuración básica
apiVersion: clickhouse.com/v1alpha1
kind: ClickHouseCluster
metadata:
name: my-cluster
spec:
replicas: 3 # Número de réplicas por segmento
shards: 2 # Número de segmentos
keeperClusterRef:
name: my-keeper # Referencia al KeeperCluster
dataVolumeClaimSpec:
resources:
requests:
storage: 10GiRéplicas y segmentos
- Réplicas: Número de instancias de ClickHouse por segmento (para alta disponibilidad)
- Segmentos: Número de particiones horizontales (para el escalado)
spec:
replicas: 3 # Predeterminado: 3
shards: 2 # Predeterminado: 1Un clúster con replicas: 3 y shards: 2 creará 6 pods de ClickHouse en total.
Integración de Keeper
Cada clúster de ClickHouse debe hacer referencia a un KeeperCluster para coordinarse:
spec:
keeperClusterRef:
name: my-keeper
# namespace: keeper-system # Opcional, por defecto usa el espacio de nombres de ClickHouseClusterCuando se establece keeperClusterRef.namespace, el operador debe observar ambos espacios de nombres. Si WATCH_NAMESPACE está configurado, incluya los espacios de nombres de ClickHouse y Keeper en esa lista.
Configuración de KeeperCluster
apiVersion: clickhouse.com/v1alpha1
kind: KeeperCluster
metadata:
name: my-keeper
spec:
replicas: 3 # Debe ser impar: 1, 3, 5, 7, 9, 11, 13 o 15
dataVolumeClaimSpec:
resources:
requests:
storage: 5GiConfiguración de almacenamiento
Configure el almacenamiento persistente con dataVolumeClaimSpec, un
PersistentVolumeClaimSpec estándar de Kubernetes. El operador lo convierte en un PersistentVolumeClaim por
réplica montado en la ruta de datos /var/lib/clickhouse:
spec:
dataVolumeClaimSpec:
storageClassName: fast-ssd # Optional: consider your storage class based on the installed CSI
resources:
requests:
storage: 100GiLa adición de discos adicionales en una configuración de varios discos (JBOD), la ejecución sin un volumen persistente, la ampliación de la capacidad, las políticas de almacenamiento personalizadas, el cifrado en reposo y las reglas sobre lo que no puede cambiar después de la creación se tratan en la guía de almacenamiento y volúmenes.
Dominio del clúster
spec.clusterDomain establece el sufijo DNS de Kubernetes que usa el operador al generar
los nombres de host completos de los pods de Kubernetes que escribe en la
configuración de servidor ClickHouse. Su valor predeterminado es cluster.local y está disponible tanto en
ClickHouseCluster como en KeeperCluster.
spec:
clusterDomain: cluster.local # default; override only for a custom domainPara las réplicas de ClickHouse, el operador crea un Service headless principal <cluster-name>-clickhouse-headless que atiende el tráfico de los clientes.
También crea servicios por réplica <cluster-name>-clickhouse-internal-<shard>-<index> que exponen Pods no listos para el tráfico interno
y las solicitudes de administración del operador. Esto puede utilizarse para la recuperación de una réplica si no logra estar lista por sí misma.
Los nodos de Keeper usan nombres de pods de Kubernetes a través de su Service headless: <pod>.<headless-service>.<namespace>.svc.<clusterDomain>.
Configuración del pod de Kubernetes
Dispersión de topología y afinidad automáticas
Distribuya los pods entre las zonas de disponibilidad:
spec:
podTemplate:
topologyZoneKey: topology.kubernetes.io/zone
nodeHostnameKey: kubernetes.io/hostnameConfiguración manual
Se pueden especificar reglas arbitrarias de afinidad/antiafinidad de pod de Kubernetes y restricciones de distribución topológica.
spec:
podTemplate:
affinity:
<your-affinity-rules-here>
topologySpreadConstraints:
<your-topology-spread-constraints-here>Consulta la Referencia de la API para ver todas las opciones compatibles de la plantilla de pod de Kubernetes.
Presupuestos de interrupción de pods
El operador crea un PodDisruptionBudget (PDB) para cada clúster, de modo que las interrupciones voluntarias — drenado de nodos, actualizaciones progresivas y desalojos del autoscaler — no puedan dejar fuera de servicio suficientes pods como para perder el quórum o comprometer la disponibilidad.
En los clústeres de ClickHouse con más de un segmento, se crea un PDB por segmento para que una interrupción en un segmento no se impute a otro.
Valores predeterminados
El operador elige valores predeterminados seguros según el tamaño del clúster, de modo que un apply inicial ya proteja frente a una pérdida accidental de quorum.
| Recurso | Topología | PDB predeterminado |
|---|---|---|
ClickHouseCluster |
replicas: 1 (segmento con una sola réplica) |
maxUnavailable: 1 — se permite la interrupción en un clúster de un solo nodo para que el drenaje de nodos no quede bloqueado |
ClickHouseCluster |
replicas: 2+ (segmento con varias réplicas) |
minAvailable: 1 — al menos una réplica por segmento debe permanecer activa |
KeeperCluster |
replicas: 1 |
maxUnavailable: 1 — se permite la interrupción en un clúster de un solo nodo para que el drenaje de nodos no quede bloqueado |
KeeperCluster |
replicas: 3+ |
maxUnavailable: replicas/2 — preserva el quorum de RAFT para un clúster 2F+1 (3 réplicas toleran 1 caída, 5 réplicas toleran 2 caídas) |
Para un ClickHouseCluster de 3 segmentos con replicas: 3, el operador crea tres PDB, uno por segmento, cada uno con minAvailable: 1.
Sobrescribir los valores predeterminados
Usa spec.podDisruptionBudget para sobrescribir minAvailable o maxUnavailable (exactamente uno):
spec:
replicas: 3
shards: 2
podDisruptionBudget:
minAvailable: 2 # mantener al menos 2 de 3 réplicas en cada segmento activas durante una interrupciónO bien la forma maxUnavailable, con un porcentaje:
spec:
replicas: 5
podDisruptionBudget:
maxUnavailable: 40%También puedes pasar el campo unhealthyPodEvictionPolicy al PDB generado, lo que resulta útil cuando necesitas permitir la expulsión de pods que aún siguen en NotReady:
spec:
podDisruptionBudget:
minAvailable: 2
unhealthyPodEvictionPolicy: AlwaysAllowPolíticas
spec.podDisruptionBudget.policy te permite elegir con qué nivel de agresividad el operador gestiona los PDB:
| Policy | Behavior |
|---|---|
Enabled (default) |
El operador crea y actualiza el PDB en cada reconciliación. Esta es la opción predeterminada segura para producción. |
Disabled |
El operador no crea PDB y elimina cualquier PDB existente con etiquetas coincidentes. Resulta útil para clústeres de desarrollo en los que deba permitirse cualquier interrupción voluntaria. |
Ignored |
El operador no crea ni elimina PDB. Los PDB existentes se dejan tal cual. Úsalo cuando otro sistema (p. ej., una política de admisión o una herramienta de GitOps) gestione los PDB por ti. |
Ejemplo — deshabilita por completo la gestión de PDB en un clúster de desarrollo:
spec:
podDisruptionBudget:
policy: DisabledEjemplo — mantén tu PDB definido manualmente junto al clúster y evita que el operador lo toque:
spec:
podDisruptionBudget:
policy: IgnoredDesactivación a nivel de clúster
La gestión de PDB también puede deshabilitarse a nivel de clúster mediante la variable de entorno ENABLE_PDB del operador. Con ENABLE_PDB=false, el operador omite el paso de reconciliación de PDB para todos los ClickHouseCluster y KeeperCluster, independientemente de su spec.podDisruptionBudget.policy, y no observa en absoluto los recursos PodDisruptionBudget. Por lo tanto, el ServiceAccount del operador no necesita permisos de RBAC sobre poddisruptionbudgets.policy/v1, lo cual resulta útil cuando el operador se ejecuta con un ServiceAccount restringido que omite intencionadamente esos permisos.
# en la especificación de Implementación del operador
env:
- name: ENABLE_PDB
value: "false"Esto está pensado para entornos que incorporan sus propias políticas de interrupción (p. ej., mediante Gatekeeper / Kyverno) y quieren que el operador quede completamente fuera del proceso.
Configuración del contenedor
Imagen personalizada
Usa una imagen concreta de ClickHouse:
spec:
containerTemplate:
image:
repository: clickhouse/clickhouse-server
tag: "25.12"
imagePullPolicy: IfNotPresentRecursos de los contenedores
Configure la CPU y la memoria de los contenedores de ClickHouse:
# default values
spec:
containerTemplate:
resources:
requests:
cpu: "250m"
memory: "512Mi"
limits:
cpu: "1"
memory: "512Mi"Variables de entorno
Añada variables de entorno personalizadas:
spec:
containerTemplate:
env:
- name: CUSTOM_ENV_VAR
value: "1"Montajes de volúmenes
Agregue montajes de volúmenes adicionales:
spec:
containerTemplate:
volumeMounts:
- name: custom-config
mountPath: /etc/clickhouse-server/config.d/custom.xml
subPath: custom.xmlConsulta la referencia de la API para ver todas las opciones compatibles de la plantilla de contenedor.
Configuración de TLS/SSL
Configurar endpoints seguros
Pasa una referencia a un Secret de Kubernetes con certificados TLS para habilitar endpoints seguros
spec:
settings:
tls:
enabled: true
required: true # Los puertos no seguros se deshabilitan si se establece
serverCertSecret:
name: <certificate-secret-name>Formato del Secret del certificado SSL
Se espera que el Secret contenga el par de claves del server:
tls.crt- certificado del server codificado en PEMtls.key- private key codificada en PEM
Comunicación de ClickHouse-Keeper mediante TLS
Si KeeperCluster tiene TLS habilitado, ClickHouseCluster usará automáticamente una conexión segura a los nodos de Keeper.
ClickHouseCluster verifica los certificados de los nodos de Keeper con el almacén de confianza del sistema, además de cualquier caBundle que configure.
Para confiar en una CA privada (por ejemplo, una CA autofirmada o interna), proporcione una referencia a un bundle de CA personalizado:
spec:
settings:
tls:
caBundle:
name: <ca-certificate-secret-name>
key: <ca-certificate-key>Secret externo
De forma predeterminada, el operador crea y controla un Secret que contiene las credenciales internas del clúster (contraseña entre servidores, contraseña de administración, identidad de Keeper, secreto del clúster y clave de colecciones con nombre). El Secret toma el nombre del clúster y reside en el espacio de nombres del clúster.
Si quiere gestionar estas credenciales usted mismo —por ejemplo, obteniéndolas de HashiCorp Vault, AWS Secrets Manager o External Secrets Operator—, haga que el operador apunte a un Secret ya existente mediante spec.externalSecret:
apiVersion: clickhouse.com/v1alpha1
kind: ClickHouseCluster
metadata:
name: sample
spec:
replicas: 2
keeperClusterRef:
name: sample
dataVolumeClaimSpec:
resources:
requests:
storage: 10Gi
externalSecret:
name: my-clickhouse-credentials
policy: ObserveClaves requeridas
El Secret debe contener las siguientes claves:
| Clave | Formato | Cuándo es obligatoria |
|---|---|---|
interserver-password |
contraseña en texto plano | Siempre |
management-password |
contraseña en texto plano | Siempre |
keeper-identity |
clickhouse:<password> |
Siempre |
cluster-secret |
contraseña en texto plano | Siempre |
named-collections-key |
clave AES de 16 bytes codificada en hexadecimal (32 caracteres hexadecimales) | Solo en ClickHouse >= 25.12 |
disk-encryption-key |
clave AES de 16 bytes codificada en hexadecimal (32 caracteres hexadecimales) | Solo cuando se establece settings.encryption |
Un Secret completo tiene este aspecto:
apiVersion: v1
kind: Secret
metadata:
name: my-clickhouse-credentials
namespace: sample
type: Opaque
stringData:
interserver-password: "a-strong-random-password"
management-password: "another-strong-password"
keeper-identity: "clickhouse:keeper-auth-password"
cluster-secret: "cluster-internal-secret"
named-collections-key: "0123456789abcdef0123456789abcdef" # 32 hex chars = 16 bytes
disk-encryption-key: "00112233445566778899aabbccddeeff" # only when settings.encryption is setPolítica: Observe vs Manage
spec.externalSecret.policy controla cómo el operador maneja las claves requeridas que faltan:
| Política | Comportamiento cuando faltan claves |
|---|---|
Observe (predeterminada) |
La reconciliación queda bloqueada hasta que estén presentes todas las claves requeridas. El operador informa de cada clave que falta —y de la indicación de formato correspondiente— mediante la condición ExternalSecretValid (con el motivo ExternalSecretInvalid) y un evento Warning. |
Manage |
El operador genera cualquier clave requerida que falte y la vuelve a escribir en el mismo Secret. Resulta útil para el aprovisionamiento inicial: crea un Secret vacío, deja que el operador lo complete y, después, opcionalmente, restringe el acceso. Aun así, el operador nunca elimina el Secret. |
Elige Observe cuando un sistema externo (Vault, ESO, sealed-secrets, GitOps) sea la fuente de referencia y quieras que el operador falle claramente ante una configuración incorrecta. Elige Manage cuando quieras un aprovisionamiento inicial autosuficiente, pero también conservar la propiedad del propio objeto Secret (por ejemplo, para hacer una copia de seguridad).
Condición de estado y solución de problemas
El operador expone una condición ExternalSecretValid en ClickHouseCluster.status.conditions. Revísala cuando parezca que la reconciliación está atascada:
# Plain kubectl — works out of the box
kubectl describe clickhousecluster sample | sed -n '/Conditions:/,$p'
# Same data as YAML
kubectl get clickhousecluster sample -o yaml | sed -n '/conditions:/,/^[^ ]/p'
# Pretty-printed JSON (requires jq)
kubectl get clickhousecluster sample -o jsonpath='{.status.conditions}' | jqPosibles razones:
reason |
Significado | Solución |
|---|---|---|
ExternalSecretNotFound |
El Secret referenciado no existe en el espacio de nombres. | Crea el Secret o corrige spec.externalSecret.name. |
ExternalSecretInvalid |
El Secret existe, pero no tiene las claves requeridas (solo con Observe). El mensaje enumera cada clave faltante junto con su formato esperado. |
Agrega las claves faltantes o cambia a policy: Manage. |
ExternalSecretValid |
Todas las claves requeridas están presentes y el operador está usando el Secret. | — |
El operador vuelve a encolar la reconciliación mientras el Secret no sea válido, así que, en cuanto agregues las claves faltantes, la siguiente reconciliación las detectará automáticamente; no hace falta reiniciar los pods.
Puertos adicionales
El operador expone un conjunto fijo de puertos en cada pod de Kubernetes de ClickHouse y en su Service headless público: 8123 para HTTP, 9000 nativo, 9009 entre servidores, 9001/9002 de administración, 9363 para métricas de Prometheus, y las variantes TLS 8443/9440 cuando TLS está habilitado. Los puertos interserver y de administración también se exponen a través de los Services internos por réplica para que las réplicas y el operador puedan comunicarse antes de que una réplica esté lista. Para que ClickHouse escuche en protocolos adicionales —MySQL, PostgreSQL, gRPC o cualquier puerto personalizado—, declárelos en spec.additionalPorts:
spec:
additionalPorts:
- name: mysql
port: 9004
- name: postgres
port: 9005
- name: grpc
port: 9100El operador añade esos puertos a containerPorts del pod de Kubernetes y al Service headless público.
El ejemplo completo se encuentra en examples/custom_protocols.yaml.
Ejemplo completo: MySQL wire protocol
Para exponer ClickHouse mediante el MySQL wire protocol en el puerto 9004:
apiVersion: clickhouse.com/v1alpha1
kind: ClickHouseCluster
metadata:
name: sample
spec:
replicas: 1
keeperClusterRef:
name: sample
dataVolumeClaimSpec:
resources:
requests:
storage: 2Gi
# 1) Open the port on the Pod and the public headless Service.
additionalPorts:
- name: mysql
port: 9004
# 2) Tell ClickHouse server to actually listen on it.
settings:
extraConfig:
protocols:
mysql:
type: mysql
port: 9004
description: "MySQL wire protocol"Una vez aplicado, verifique desde dentro del clúster:
kubectl exec sample-clickhouse-0-0-0 -- \
clickhouse-client --port 9004 --query "SELECT 1"Restricciones de los campos
| Campo | Regla |
|---|---|
name |
Debe coincidir con el patrón DNS_LABEL ^[a-z]([-a-z0-9]*[a-z0-9])?$, con un máximo de 63 caracteres. El CRD aplica la unicidad como clave list-map. |
port |
Entero en [1, 65535]. El webhook rechaza números de puerto duplicados en la lista. |
Puertos y nombres reservados
El webhook de validación rechaza las entradas de additionalPorts que entrarían en conflicto con los puertos en los que el propio operador escucha. Todos los puertos relacionados con TLS están reservados incondicionalmente para que habilitar spec.settings.tls.enabled más adelante no invalide un clúster que antes era válido.
| Port | Reservado para |
|---|---|
8123 |
HTTP |
8443 |
HTTPS |
9000 |
native TCP |
9440 |
TLS nativo |
9009 |
interserver |
9001 |
management |
9363 |
métricas de Prometheus |
Los siguientes nombres también se rechazan: son los identificadores internos del operador para tipos de protocolo (no los alias legibles para humanos):
| Name |
|---|
http |
http-secure |
tcp |
tcp-secure |
interserver |
management |
prometheus |
Una solicitud rechazada produce un error como:
spec.additionalPorts[0].port: 8123 is reserved for the operator-managed HTTP port
spec.additionalPorts[0].name: "http" is reserved by the operatorSonda de versión y canal de actualización
El operador realiza dos tareas independientes con las versiones del clúster:
- Informe de versión — para
ClickHouseCluster, unJobde Kubernetes ejecuta la imagen de contenedor una vez para detectar la versión de ClickHouse en ejecución; paraKeeperCluster, el operador lee la versión informada por el servidor desde las réplicas en ejecución. La versión detectada se registra en.status.versiony se utiliza en otros pasos de reconciliación (por ejemplo, la clave de named collections deExternal Secretsolo es necesaria a partir de ClickHouse25.12). - Canal de actualización — una comprobación periódica del feed público de versiones de ClickHouse (
https://clickhouse.com/data/version_date.tsv). El operador informa si hay una versión más reciente disponible mediante la condición de estadoVersionUpgraded. Nunca actualiza el clúster por sí solo; el usuario controla la etiqueta de la imagen.
Elegir un canal de lanzamientos
spec.upgradeChannel selecciona con qué conjunto de lanzamientos upstream compara el operador. El mismo campo existe tanto en ClickHouseCluster como en KeeperCluster.
spec:
upgradeChannel: lts # or "stable", or "25.8", or omittedValores permitidos (validados por la CRD con el patrón ^(lts|stable|\d+\.\d+)?$):
| Valor | Comportamiento |
|---|---|
| vacío (predeterminado) | El operador propone solo actualizaciones menores dentro de la línea major.minor que se está ejecutando actualmente. A un cluster en 25.8.3.1 se le notificará sobre 25.8.4.x, pero no sobre 25.9.x. |
stable |
Sigue el canal stable de upstream: la última versión que ClickHouse Inc. marca como estable en la línea principal de releases. Recibe actualizaciones mayores antes que el canal lts. |
lts |
Sigue el canal lts de upstream: releases con soporte a largo plazo. Recibe actualizaciones mayores con menos frecuencia y con ventanas de soporte más largas. |
25.8 (o cualquier <major>.<minor>) |
Fija el canal en una línea major.minor específica. No se proponen actualizaciones mayores más allá de esa línea, aunque exista una versión más reciente en upstream. |
Para production, en general se prefiere fijar el canal a un <major>.<minor> explícito (por ejemplo, 25.8). Esto fija el cluster en la línea de release mayor prevista y permite que el operador mustre una advertencia WrongReleaseChannel si alguna réplica se desvía de algún modo a una major distinta, algo especialmente importante cuando la image se referencia mediante un digest (@sha256:...) en lugar de un tag legible para humanos. El valor predeterminado vacío es adecuado para clusters de Development en los que los saltos entre versiones major no son una preocupación.
Condiciones de estado
Dos condiciones reflejan el resultado de la sonda y de la comprobación de actualización:
| Condición | Motivo | Significado |
|---|---|---|
VersionInSync |
VersionMatch |
Todas las réplicas informan la misma versión |
VersionInSync |
VersionMismatch |
Las réplicas están ejecutando versiones distintas. Este motivo se suprime durante una actualización gradual planificada. Suele aparecer cuando se ha fijado una etiqueta de imagen mutable (por ejemplo, latest o una versión major sin más, como 26.3) y el registry subyacente ha cambiado entre una descarga y otra, por lo que distintas réplicas acabaron con parches diferentes de la misma etiqueta. |
VersionInSync |
VersionPending |
El Job de la sonda de versión aún no ha terminado, o todavía no se ha observado ninguna versión de réplica de Keeper |
VersionInSync |
VersionProbeFailed |
El Job de la sonda de ClickHouse falló; el operador no puede determinar la versión en ejecución |
VersionUpgraded |
UpToDate |
El cluster está en la versión más reciente disponible en el canal seleccionado |
VersionUpgraded |
MinorUpdateAvailable |
Hay un parche más reciente disponible en la misma línea major.minor |
VersionUpgraded |
MajorUpdateAvailable |
Hay una versión major.minor más reciente disponible dentro del canal elegido |
VersionUpgraded |
VersionOutdated |
La versión en ejecución está desactualizada y ya no recibirá correcciones del canal seleccionado; normalmente porque la línea major se ha retirado de lts o stable upstream |
VersionUpgraded |
WrongReleaseChannel |
La imagen en ejecución no pertenece al upgradeChannel seleccionado. Ejemplo: un cluster que ejecuta 26.5 con upgradeChannel: lts, ya que 26.5 no forma parte de la línea lts upstream. |
VersionUpgraded |
UpgradeCheckFailed |
El operador no pudo acceder al feed de versiones upstream |
Inspecciónalas con:
kubectl get clickhousecluster sample -o yaml | sed -n '/conditions:/,/^[^ ]/p'Sobrescritura del Job de la sonda de versión
Esto se aplica solo a ClickHouseCluster. KeeperCluster ya no ejecuta un Job de sonda de versión; su versión se lee directamente de las réplicas de Keeper en ejecución, por lo que spec.versionProbeTemplate está obsoleto y no tiene efecto allí.
La sonda se implementa como un Job estándar de Kubernetes. Si su clúster tiene políticas de admisión que exigen Tolerations específicas, selectores de nodo o contextos de seguridad, o si desea limitar cuánto tiempo permanecen los Jobs de sonda completados, sobrescriba la plantilla mediante spec.versionProbeTemplate:
spec:
versionProbeTemplate:
spec:
ttlSecondsAfterFinished: 600 # delete completed probe Jobs 10 minutes after completion
template:
spec:
nodeSelector:
kubernetes.io/arch: amd64
tolerations:
- key: dedicated
operator: Equal
value: clickhouse
effect: NoSchedule
containers:
- name: version-probe
resources:
requests:
cpu: 50m
memory: 64MiEl nombre del contenedor version-probe es el predeterminado del operador: la entrada en containers: coincide con él por nombre, por lo que el operador aplica una fusión profunda de los campos proporcionados por el usuario sobre los valores predeterminados.
Controles globales del operador
Dos opciones del administrador del operador controlan globalmente el bucle de comprobación de actualizaciones:
| Opción | Predeterminado | Efecto |
|---|---|---|
--version-update-interval |
24h |
Frecuencia con la que el operador vuelve a obtener la lista de versiones del origen |
--disable-version-update-checks |
false |
Desactiva por completo la comprobación de actualizaciones. No se establece la condición VersionUpgraded y no se genera tráfico HTTP saliente a clickhouse.com |
Establece --disable-version-update-checks=true en entornos aislados de la red o cuando no se permite la salida a clickhouse.com.
Configuración de ClickHouse
Contraseña del usuario default
spec.settings.defaultUserPassword establece la contraseña del usuario default
integrado. Proporcione el valor de una clave de un Secret (recomendado) o de un ConfigMap que
cree, en lugar de incluirlo directamente en el CR:
spec:
settings:
defaultUserPassword:
passwordType: password # default; see "Password types" below
secret: # exactly one of secret or configMap
name: clickhouse-password # name of the Secret/ConfigMap
key: password # the key inside it, not the password valueProporcione exactamente uno de secret o configMap, y en ambos casos name (el objeto)
y key (la entrada que contiene la contraseña).
Tipos de contraseña
passwordType le indica a ClickHouse cómo interpretar el valor. De forma predeterminada, es
password (texto plano); las alternativas son formas con hash, como
password_sha256_hex y password_double_sha1_hex. Se recomienda usar un tipo con hash para que la
contraseña en texto plano nunca se almacene. Consulte la
configuración de usuarios de ClickHouse
para ver la lista completa.
Ejemplo completo con un Secret
Crea el Secret y, a continuación, haz referencia a su clave:
kubectl create secret generic clickhouse-password \
--from-literal=password='your-secure-password'apiVersion: clickhouse.com/v1alpha1
kind: ClickHouseCluster
metadata:
name: my-cluster
spec:
settings:
defaultUserPassword:
passwordType: password
secret:
name: clickhouse-password
key: passwordSi usas una contraseña con hash, almacena el hash en lugar del texto plano:
echo -n 'your-secure-password' | sha256sum # use the hex digest as the value
kubectl create secret generic clickhouse-password \
--from-literal=password='<sha256-hex-digest>'spec:
settings:
defaultUserPassword:
passwordType: password_sha256_hex
secret:
name: clickhouse-password
key: passwordUso de un ConfigMap
Un ConfigMap funciona de la misma manera, pero su contenido no está protegido como un Secret.
Úselo solo para valores no confidenciales o con hash previo, como un
resumen password_sha256_hex:
spec:
settings:
defaultUserPassword:
passwordType: password_sha256_hex
configMap:
name: clickhouse-config
key: default_passwordUsuarios personalizados en la configuración
Configure usuarios adicionales en los archivos de configuración.
Cree un ConfigMap y un Secret para el usuario:
apiVersion: v1
kind: ConfigMap
metadata:
name: user-config
data:
reader.yaml: |
users:
reader:
password:
- '@from_env': READER_PASSWORD
profile: default
grants:
query:
- "GRANT SELECT ON *.*"
---
apiVersion: v1
kind: Secret
metadata:
name: reader-password
data:
password: "c2VjcmV0LXBhc3N3b3Jk" # base64("secret-password")Añade una configuración personalizada a ClickHouseCluster:
spec:
podTemplate:
volumes:
- name: reader-user
configMap:
name: user-config
containerTemplate:
env:
- name: READER_PASSWORD
valueFrom:
secretKeyRef:
name: reader-password
key: password
volumeMounts:
- mountPath: /etc/clickhouse-server/users.d/
name: reader-user
readOnly: trueSincronización de la base de datos
Habilite la sincronización automática de la base de datos para las nuevas réplicas:
spec:
settings:
enableDatabaseSync: true # Default: trueCuando está activado, el operador sincroniza las tablas Replicated y de integración en las nuevas réplicas.
Cada pod de Kubernetes de réplica incluye la puerta de readiness clickhouse.com/ReplicaInitialized, por lo que una nueva réplica se publica mediante el Service headless público solo después de que el operador complete su inicialización: la base de datos default se convierte al engine Replicated y se sincroniza el esquema. Hasta entonces, el operador y las demás réplicas acceden a ella mediante su Service interno. Con enableDatabaseSync: false, el operador marca las réplicas como inicializadas de inmediato, por lo que la readiness depende únicamente de los probes del contenedor.
El operador nunca elimina una base de datos default no Replicated poblada. Dicha réplica sigue atendiendo tráfico de clientes después de la preparación del esquema, pero el clúster informa SchemaInSync=False con el motivo DefaultDatabaseNotReplicated hasta que resuelva esa base de datos por su cuenta.
Antes de eliminar una réplica durante una reducción de escala, el operador primero retira de ella el tráfico de clientes, espera hasta que deje de publicarse, replica sus datos restantes en las réplicas supervivientes y solo entonces la elimina.
Registro del servidor
Configure el registro del ClickHouse server mediante spec.settings.logger. Todos los campos son opcionales y tienen valores predeterminados seguros, por lo que incluso un clúster que no modifique registrará en trace tanto en la consola del contenedor como en un archivo rotado en disco.
spec:
settings:
logger:
logToFile: true # Default: true. Set false to log only to the console
jsonLogs: false # Default: false. Set true for structured JSON log lines
level: trace # Default: trace
size: 1000M # Default: 1000M. Rotate a log file once it reaches this size
count: 50 # Default: 50. Number of rotated files to keep| Campo | Predeterminado | Descripción |
|---|---|---|
logToFile |
true |
Cuando es false, el operador elimina los destinos de archivo y el servidor solo escribe logs en la consola del contenedor. |
jsonLogs |
false |
Cuando es true, el operador añade formatting.type: json para que cada línea sea un objeto JSON. |
level |
trace |
Nivel de detalle de los logs. Uno de test, trace, debug, information, notice, warning, error, critical, fatal. |
size |
1000M |
Tamaño máximo de un solo archivo de log antes de la rotación. |
count |
50 |
Número de archivos de log rotados que conserva el servidor. |
El operador siempre mantiene activado el registro en consola para que kubectl logs funcione, y añade el registro en archivo cuando logToFile es true. Un clúster con los valores predeterminados genera este bloque logger:
logger:
console: true
level: trace
log: /var/log/clickhouse-server/clickhouse-server.log
errorlog: /var/log/clickhouse-server/clickhouse-server.err.log
size: 1000M
count: 50El mismo bloque spec.settings.logger se aplica a un KeeperCluster; en ese caso, el operador escribe sus archivos en /var/log/clickhouse-keeper/.
Configuración personalizada
Configuración adicional integrada
En lugar de montar archivos de configuración personalizados, puedes especificar directamente opciones adicionales de configuración de ClickHouse.
Agrega una configuración personalizada de ClickHouse con extraConfig:
spec:
settings:
extraConfig:
background_pool_size: 20Enlaces útiles:
Configuración integrada de usuarios adicionales
También puedes especificar la configuración adicional de usuarios de ClickHouse mediante extraUsersConfig. Esto es útil para definir usuarios, perfiles, cuotas y privilegios directamente en la especificación del clúster.
spec:
settings:
extraUsersConfig:
users:
analyst:
password:
- '@from_env': ANALYST_PASSWORD
profile: "readonly"
quota: "default"
profiles:
readonly:
readonly: 1
max_memory_usage: 10000000000
quotas:
default:
interval:
duration: 3600
queries: 1000
errors: 100Consulta la documentación para ver todas las opciones de configuración de usuarios de ClickHouse admitidas.
Ejemplo de configuración
Ejemplo completo de configuración:
apiVersion: clickhouse.com/v1alpha1
kind: KeeperCluster
metadata:
name: sample
spec:
replicas: 3
dataVolumeClaimSpec:
storageClassName: <storage-class-name>
resources:
requests:
storage: 10Gi
podTemplate:
topologyZoneKey: topology.kubernetes.io/zone
nodeHostnameKey: kubernetes.io/hostname
containerTemplate:
resources:
requests:
cpu: "2"
memory: "4Gi"
limits:
cpu: "4"
memory: "8Gi"
settings:
tls:
enabled: true
required: true
serverCertSecret:
name: <keeper-certificate-secret>
---
apiVersion: v1
kind: ConfigMap
metadata:
name: default-user-password
data:
# contraseña-secreta
password: "..." # sha256 hex de la contraseña
---
apiVersion: clickhouse.com/v1alpha1
kind: ClickHouseCluster
metadata:
name: sample
spec:
replicas: 2
dataVolumeClaimSpec:
storageClassName: <storage-class-name>
resources:
requests:
storage: 200Gi
keeperClusterRef:
name: sample
podTemplate:
topologyZoneKey: topology.kubernetes.io/zone
nodeHostnameKey: kubernetes.io/hostname
settings:
tls:
enabled: true
required: true
serverCertSecret:
name: clickhouse-cert
defaultUserPassword:
passwordType: password_sha256_hex
configMap:
key: password
name: default-password