輕鬆整合系列三:如何在 KubeBlocks 中配置引數模板|以 Oracle MySQL 為例

小猿姐聊技術發表於2023-12-27

本文以 Oracle MySQL 為例,介紹如何在KubeBlocks中配置引數模板。

前提條件

  1. 瞭解 K8s 基本概念,例如 Pod,ConfigMap 等。

  2. 完成 Tutorial 1。

  3. 瞭解 Go Template(非必須)。

背景知識

在建立 Cluster 時,我們通常會根據資源情況、效能需求、環境等資訊調整引數。雲資料庫廠商,如 AWS、Aliyun 也提供了不同的引數模版(例如 RDS 有高效能模版,非同步模版等)供使用者選擇,快速啟動。

在本文中,我們會介紹 Kubeblocks 中引數配置的相關內容,包括如何新增引數模版、如何修改引數、如何配置引數校驗。

在 K8s 中,使用者可將引數檔案以 ConfigMap 的形式掛載到 Pod 的捲上。

但是 K8s 只管理 ConfigMap 的更新,並將其同步到 Pod 捲上。如果資料庫引擎不支援動態載入配置檔案(例如 MySQL,Postgres),那我們只能登入資料庫並執行更新操作。透過直接登入資料庫的方式操作,就很容易導致配置漂移。

為了防止配置漂移,KubeBlocks 是透過 ConfigMap 來管理引數,且秉持理念是: ConfigMap is the only source-of-truth,即所有配置的變更都是先應用到 ConfigMap 上,然後根據引數的不同生效方式,再應用到 Cluster 的每個 Pod 上。引數/配置更新的話題我們會在下一個教程中詳細說明。

ConfigTemplate 配置模板/引數模板

KubeBlocks 透過  Go Template 來渲染引數模版,除了常見函式,還內建了一些資料庫中常用到的計算函式(例如  callBufferSizeByResourcegetContainerCPU

KubeBlocks 增強的渲染能力,能讓你快速定製一個 自適應引數模板(Adaptive ConfigTemplate),可根據上下文(例如記憶體、CPU 大小)來渲染合適的配置檔案。

新增引數模版

apiVersion: v1
kind: ConfigMap
metadata:
  name: oracle-mysql-config-template
  labels:
    {{- include "oracle-mysql.labels" . | nindent 4 }}
data:
  my.cnf: |-
    {{`
      [mysqld]
      port=3306
      {{- $phy_memory := getContainerMemory ( index $.podSpec.containers 0 ) }}
      {{- $pool_buffer_size := ( callBufferSizeByResource ( index $.podSpec.containers 0 ) ) }}
      {{- if $pool_buffer_size }}
      innodb_buffer_pool_size={{ $pool_buffer_size }}
      {{- end }}
      # if memory less than 8Gi, disable performance_schema
      {{- if lt $phy_memory 8589934592 }}
      performance_schema=OFF
      {{- end }}
      [client]
      port=3306
      socket=/var/run/mysqld/mysqld.sock
      `
    }}

Figure 1. ConfigTemplate for Oracle MySQL

Figure 1. 展示了一個透過 ConfigMap 定義的 MySQL 的 自適應引數模板。

模板中配置了幾個常見的 mysql 引數,包括 port,innodb_buffer_pool_size 等。

它根據容器啟動時配置的 memory

  • 計算得到  innodb_buffer_size 大小(line 11 ~ line 15)。

  • 並且在 memory 小於 8Gi 時,關閉  performance_schema 來減少效能影響 (line 32 ~ line 34)。

callBufferSizeByResource 是 KubeBlocks 預定義的一個 bufferPool 計算規則,主要為 MySQL 服務。

此外,你也可以透過查詢 memory 和 cpu 來定製你的計算公式:

  • getContainerMemory 獲取 Pod 上某個 container 的 memory 大小。

  • getContainerCPU 獲取 Pod 中某個 container 的 cpu 大小。

可以按照需求定製更多的引數計算方式,比如

  • 根據 memory 大小,計算出一個合適的  max_connection 值。

  • 根據 memory 總量,計算其他元件的合理配置。

使用引數模版

修改 ClusterDefinition

我們在  ClusterDefinition 可以透過  configSpecs 來指定引數模板,引用在 Figure 1. 中定義的 ConfigMap。

  componentDefs:
    - name: mysql-compdef
      configSpecs:
        - name: mysql-config
          templateRef: oracle-mysql-config-template # 定義了引數模板的 ConfigMap 名    
          volumeName: configs                       # 掛載的卷名稱                 
          namespace: {{ .Release.Namespace }}       # 該引數模板 ConfigMap 的 namespace
      podSpec:
        containers:
          - name: mysql-container
            volumeMounts:
              - mountPath: /var/lib/mysql
                name: data
              - mountPath: /etc/mysql/conf.d       # 掛載的配置檔案路徑,引擎相關    
                name: configs                      # 和 line 6 的 volumeName 對應     
            ports:
             ...

Figure 2. Specify ConfigTemplate in ClusterDefinition

如 Figure 2 所示,我們需要修改  ClusterDefinition.yaml 檔案,新增了  configSpecs 欄位(line 3 ~ 7)。

我們需要分別指定

  • templateRef:模板所在的 ConfigMap 物件名稱。

  • volumeName:掛載到 Pod 的卷名。

  • namespace:模板檔案的名空間(ConfigMap 是 namespace scope 的,一般為 KubeBlocks 安裝的名空間)。

檢視配置資訊

當一個新的 Cluster 建立後,KubeBlocks 會根據配置模板渲染好對應的 configmap,並將該 configMap 掛載到  configs 卷中。

1. 安裝 Helm chart

helm install oracle-mysql path-to-your-helm-char/oracle-mysql

2. 建立叢集

 kbcli cluster create mycluster --cluster-definition oracle-mysql --cluster-version oracle-mysql-8.0.32

3. 檢視配置

kbcli 提供了  describe-config 子命令來檢視叢集的配置資訊。

kbcli cluster describe-config mycluster --component mysql-compdef
ConfigSpecs Meta:
CONFIG-SPEC-NAME   FILE     ENABLED   TEMPLATE                       CONSTRAINT   RENDERED                               COMPONENT       CLUSTER
mysql-config       my.cnf   false     oracle-mysql-config-template                mycluster-mysql-compdef-mysql-config   mysql-compdef   mycluster
History modifications:
OPS-NAME   CLUSTER   COMPONENT   CONFIG-SPEC-NAME   FILE   STATUS   POLICY   PROGRESS   CREATED-TIME   VALID-UPDATED

可以檢視到:

  • 配置模版名:oracle-mysql-config-template

  • 渲染後的 ConfigMap:mycluster-mysql-compdef-mysql-config

  • 載入的檔名:my.cnf

總結

本文介紹了透過引數模板來渲染“自適應”引數的能力。

K8s 會將 ConfigMap 的變更定時同步到 Pod 上,但是大部分引擎並不會主動載入新的配置(比如 MySQL,PostgreSQL,Redis)。因為,我們無法僅透過修改 ConfigMap 就實現到 Reconfig(引數變更)的能力。會在下一個 Tutorial 中介紹如何配置變更。

Appendix

A.1 如何配置多個引數模版

在生產環境中,我們通常需要多個引數模板,來滿足不同需求。例如 Aliyun RDS 就提供了高效能引數模板、非同步模板等。

在 KubeBlocks 中,我們可以透過配置多個  ClusterVerion 來實現這一需求。

還記得我們對 cluster 的定義嗎,cluster 可以表示為:

Cluster=ClusterDefinition.yaml⋈ClusterVersion.yaml⋈Cluster.yaml

其中 JoinKey 就是 Component Name。

多個 ClusterVersion 可以和同一個 ClusterDefinition 組合。

## 第一個 ClusterVersion,使用 ClusterDefinition 中的配置
apiVersion: apps.kubeblocks.io/v1alpha1
kind: ClusterVersion
metadata:
  name: oracle-mysql
spec:
  clusterDefinitionRef: oracle-mysql
  componentVersions:
  - componentDefRef: mysql-compdef
    versionsContext:
      containers:
        - name: mysql-container
          ...
---
## 第二個 ClusterDefinition,定義了自己的 configSpecs,會覆蓋 ClusterDefinition 的配置
apiVersion: apps.kubeblocks.io/v1alpha1
kind: ClusterVersion
metadata:
  name: oracle-mysql-perf
spec:
  clusterDefinitionRef: oracle-mysql
  componentVersions:
  - componentDefRef: mysql-compdef
    versionsContext:
      containers:
        - name: mysql-container
         ...
    # name needs to consistent with the name of the configmap defined in clusterDefinition
    configSpecs:
      - name: mysql-config    
        templateRef: oracle-mysql-perf-config-template
        volumeName: configs

Figure 3. Specify ConfigTemplates in ClusterVersion

Figure 3. 建立了兩個  ClusterVersion 物件。

第一個使用了預設的引數模版(沒有配置任何資訊)。第二個透過  configSpecs 指定了一個新的引數模版  oracle-mysql-perf-config-template

在建立 Cluster 時,我們可以指定  ClusterVersion 引數來建立不同配置的Cluster,如:

kbcli cluster create mysqlcuster --cluster-definition oracle-mysql --cluster-version  oracle-mysql-perf

注意:KubeBlocks 會透過  configSpecs.name 來合併 ClusterVersion 和 ClusterDefinition 中的配置。因此我們必須確保在 ClusterVersion 中定義的  configSpecs.name 和 ClusterDefinition 中定義的名稱一致。


來自 “ ITPUB部落格 ” ,連結:https://blog.itpub.net/70035809/viewspace-3001780/,如需轉載,請註明出處,否則將追究法律責任。

相關文章