TECHSTEP

ITインフラ関連の記事を公開してます。

Rook-Cephの機能紹介(Block Storage編)

はじめに

Rook-Cephの設定や機能について、公式ドキュメントをベースにまとめています。今回はCephで利用できるストレージのうち、ブロックストレージを利用するために必要な情報について、Ceph Cluster CRDの内容をまとめます。公式ドキュメントでは、利用方法についてのサンプル集が載っているので、そちらを中心に紹介します。

検証環境

Block Storage

Rook-Cephでブロックストレージを利用する場合、以下の流れで構築を行います。

  1. CephClusterの作成
  2. CephBlockPoolの作成
  3. Storage Classの作成
  4. ブロックストレージの利用

こちらの構築については、以前紹介したこちらの手順を参照してください。以降では、クラスター構築時に利用できる各設定項目を、サンプルファイルと併せて記載します。

Ceph Cluster CRD

Storage Configuration: Specific devices

クラスターに含まれる特定のノードを指定してOSDに利用します。spec.storage.nodesでノードを指定し、各ノードでディレクトリ・デバイスを指定することで、特定のノード内の指定したストレージリソースを消費できます。

  • spec.storage: OSD関連の設定を指定する

サンプル例

以下のyamlファイルを利用します。ここではvm1 vm2の2つのノードを指定し、/dataディレクトリをOSDに利用します。

apiVersion: ceph.rook.io/v1
kind: CephCluster
metadata:
  name: rook-ceph
  namespace: rook-ceph
spec:
  cephVersion:
    image: ceph/ceph:v14.2.5
    allowUnsupported: true
  dataDirHostPath: /data
  skipUpgradeChecks: false
  continueUpgradeAfterChecksEvenIfNotHealthy: false
  mon:
    count: 1
    allowMultiplePerNode: true
  dashboard:
    enabled: true
    ssl: true
  storage:
    useAllNodes: false
    useAllDevices: false
    config:
      databaseSizeMB: "1024" # this value can be removed for environments with normal sized disks (100 GB or larger)
      journalSizeMB: "1024"  # this value can be removed for environments with normal sized disks (20 GB or larger)
      osdsPerDevice: "1" # this value can be overridden at the node or device level
##### ノードとディレクトリを指定 #####
    nodes:
    - name: "vm1"
      directories:
      - path: "/data"
    - name: "vm2"
      directories:
      - path: "/data"

上記ファイルをデプロイすると、OSD Podがvm1 vm2にのみ作成されていることが確認できます。またデプロイ後は以下の通り、vm1 vm2にのみOSD用のディレクトリが作成されています。

# デプロイ後の各ノードの利用状況
## vm1

Every 2.0s: ls -l /data                                 Thu Jan 23 08:57:04 2020

total 24
drwx------ 2 root root 16384 Jan 12 12:39 lost+found
drwxr--r-- 4  167  167  4096 Jan 23 08:53 osd1
drwxr-xr-x 4 root root  4096 Jan 23 08:53 rook-ceph

## vm2
Every 2.0s: ls -l /data                                 Thu Jan 23 08:57:19 2020

total 28
drwx------ 2 root root 16384 Jan 12 12:43 lost+found
drwxr-xr-x 3 root root  4096 Jan 23 08:52 mon-a
drwxr--r-- 4  167  167  4096 Jan 23 08:53 osd0
drwxr-xr-x 4 root root  4096 Jan 23 08:52 rook-ceph

## vm3
Every 2.0s: ls -l /data                                 Thu Jan 23 08:57:28 2020

total 16
drwx------ 2 root root 16384 Jan 12 12:45 lost+found

Storage Configuration: Specific devices (デバイス利用の場合)

上記サンプル例ではディレクトリを指定していますが、ここでは追加でデバイスを指定した場合も載せておきます。

サンプル例

以下のyamlファイルでは、vm1 vm2ノードを指定し、それぞれのノードでsddバイスを利用するよう指定しています。

apiVersion: ceph.rook.io/v1
kind: CephCluster
metadata:
  name: rook-ceph
  namespace: rook-ceph
spec:
  cephVersion:
    image: ceph/ceph:v14.2.5
    allowUnsupported: true
  dataDirHostPath: /data
  skipUpgradeChecks: false
  continueUpgradeAfterChecksEvenIfNotHealthy: false
  mon:
    count: 1
    allowMultiplePerNode: true
  dashboard:
    enabled: true
    ssl: true
  storage:
    useAllNodes: false
    useAllDevices: false
    config:
      databaseSizeMB: "1024" # this value can be removed for environments with normal sized disks (100 GB or larger)
      journalSizeMB: "1024"  # this value can be removed for environments with normal sized disks (20 GB or larger)
      osdsPerDevice: "1" # this value can be overridden at the node or device level
##### ノードとデバイスを指定 #####
    nodes:
    - name: "vm1"
      devices:
      - name: "sdd"
      config:
        storeType: bluestore
    - name: "vm2"
      devices:
      - name: "sdd"
      config:
        storeType: bluestore

上記ファイルをデプロイすると、vm1 vm2OSD Podが作成されること、それぞれのsddバイス上にボリュームが作成されたことが確認できます。

# OSD Podの配置されたノードを確認

[root@vm0 ceph]# kubectl get pods -n rook-ceph -o wide
NAME                                            READY   STATUS        RESTARTS   AGE     IP             NODE   NOMINATED NODE   READINESS GATES
csi-cephfsplugin-4j6qz                          3/3     Running       0          2m11s   10.0.1.7       vm2    <none>           <none>
csi-cephfsplugin-jdbhq                          3/3     Running       0          2m11s   10.0.1.4       vm3    <none>           <none>
csi-cephfsplugin-provisioner-8b9d48896-k22c7    4/4     Running       0          2m11s   10.244.2.218   vm2    <none>           <none>
csi-cephfsplugin-provisioner-8b9d48896-krfvh    4/4     Running       0          2m11s   10.244.3.218   vm3    <none>           <none>
csi-cephfsplugin-vjjtw                          3/3     Running       0          2m11s   10.0.1.5       vm1    <none>           <none>
csi-rbdplugin-85k5w                             3/3     Running       0          2m11s   10.0.1.4       vm3    <none>           <none>
csi-rbdplugin-bl2tp                             3/3     Running       0          2m11s   10.0.1.7       vm2    <none>           <none>
csi-rbdplugin-fgs7g                             3/3     Running       0          2m11s   10.0.1.5       vm1    <none>           <none>
csi-rbdplugin-provisioner-6d465d6c6f-4bfzd      5/5     Running       0          2m11s   10.244.1.219   vm1    <none>           <none>
csi-rbdplugin-provisioner-6d465d6c6f-nvxhk      5/5     Running       0          2m11s   10.244.3.219   vm3    <none>           <none>
rook-ceph-crashcollector-vm1-666498f4db-8l2tj   1/1     Terminating   0          90s     10.244.1.221   vm1    <none>           <none>
rook-ceph-crashcollector-vm1-87d7886d4-v29j7    1/1     Running       0          26s     10.244.1.224   vm1    <none>           <none>
rook-ceph-crashcollector-vm2-d9879bccc-j6vdf    1/1     Running       0          100s    10.244.2.222   vm2    <none>           <none>
rook-ceph-mgr-a-6d87d6c587-tsvgn                1/1     Running       0          90s     10.244.1.220   vm1    <none>           <none>
rook-ceph-mon-a-54ccd89fbb-sl4mb                1/1     Running       0          100s    10.244.2.221   vm2    <none>           <none>
rook-ceph-operator-678887c8d-7rftk              1/1     Running       0          2m33s   10.244.1.217   vm1    <none>           <none>
rook-ceph-osd-0-66b54c5d6-q6lg4                 1/1     Running       0          38s     10.244.2.224   vm2    <none>           <none>
rook-ceph-osd-1-8457d498ff-jbx59                1/1     Running       0          26s     10.244.1.223   vm1    <none>           <none>
rook-ceph-osd-prepare-vm1-296w6                 0/1     Completed     0          65s     10.244.1.222   vm1    <none>           <none>
rook-ceph-osd-prepare-vm2-m9b7t                 0/1     Completed     0          65s     10.244.2.223   vm2    <none>           <none>
rook-discover-68hcr                             1/1     Running       0          2m29s   10.244.2.217   vm2    <none>           <none>
rook-discover-l5mg5                             1/1     Running       0          2m29s   10.244.1.218   vm1    <none>           <none>
rook-discover-qs48l                             1/1     Running       0          2m29s   10.244.3.217   vm3    <none>           <none>
[root@vm0 ceph]#


# 各ノードのデバイス利用状況

## vm1

[root@vm1 ~]# lsblk
NAME                                      MAJ:MIN RM  SIZE RO TYPE MOUNTPOINT
fd0                                         2:0    1    4K  0 disk
sda                                         8:0    0   30G  0 disk
|-sda1                                      8:1    0  500M  0 part /boot
|-sda2                                      8:2    0 29.5G  0 part /
sdb                                         8:16   0   16G  0 disk
|-sdb1                                      8:17   0   16G  0 part /mnt/resource
sdc                                         8:32   0  100G  0 disk
|-sdc1                                      8:33   0  100G  0 part /data
sdd                                         8:48   0   64G  0 disk
|-ceph--028159da--8409--4efd--a8f5--6904bfef7585-osd--data--9ebae6db--d231--4b5a--b48b--653219df0b14
                                          253:0    0   63G  0 lvm

## vm2

[root@vm2 ~]# lsblk
NAME                                      MAJ:MIN RM  SIZE RO TYPE MOUNTPOINT
fd0                                         2:0    1    4K  0 disk
sda                                         8:0    0   30G  0 disk
|-sda1                                      8:1    0  500M  0 part /boot
|-sda2                                      8:2    0 29.5G  0 part /
sdb                                         8:16   0   16G  0 disk
|-sdb1                                      8:17   0   16G  0 part /mnt/resource
sdc                                         8:32   0  100G  0 disk
|-sdc1                                      8:33   0  100G  0 part /data
sdd                                         8:48   0   64G  0 disk
|-ceph--c036bbc1--a720--4720--8aeb--a2bd4af3e104-osd--data--a0579273--6450--4d9a--b3f3--68c3d01b03a2
                                          253:0    0   63G  0 lvm

Storage Configuration: Cluster wide Directories

クラスター内のすべてのノードを対象に、OSDに利用するディレクトリを指定することができます。また、一部ノードは別のディレクトリを利用したい、という場合はspec.storage.nodesで上書き指定できます。

  • spec.storage.directories: 利用するディレクトリを指定
    • path: ディレクトリパスを指定
    • config: 特定のディレクトリ専用の設定
      • metadataDevice: OSDメタデータに利用するデバイスを指定
      • storeType: filestore bluestoreのいずれかを指定。ディレクトリを利用する場合、デフォルトではfilestoreが設定される
      • journalSizeMB: filestoreジャーナルのサイズ数をMBで指定
      • osdsPerDevice: 各デバイスで作成するOSD数を指定
      • encryptedDevice: trueの場合、dmcryptを利用してOSDボリュームを暗号化する。デフォルトではfalseに設定される

サンプル例

以下のyamlファイルでは、spec.storage.directoriesを指定し、各ノードに対して共通のディレクトリを利用するようにします。そのうえで、vm3では/data/storage-dirを利用するよう指定し、vm3ノードのみ別のディレクトリを利用するよう指定します。

なお、以下のファイルではuseAllNodesfalseにし、vm1 vm3を対象ノードに指定しています。そのため、実行結果ではvm1 vm3のみでOSD Pod及びディレクトリが作成されます。

apiVersion: ceph.rook.io/v1
kind: CephCluster
metadata:
  name: rook-ceph
  namespace: rook-ceph
spec:
  cephVersion:
    image: ceph/ceph:v14.2.5
    allowUnsupported: true
  dataDirHostPath: /data
  skipUpgradeChecks: false
  continueUpgradeAfterChecksEvenIfNotHealthy: false
  mon:
    count: 1
    allowMultiplePerNode: true
  dashboard:
    enabled: true
    ssl: true
  storage:
    useAllNodes: false
    useAllDevices: false
    config:
      databaseSizeMB: "1024" # this value can be removed for environments with normal sized disks (100 GB or larger)
      journalSizeMB: "1024"  # this value can be removed for environments with normal sized disks (20 GB or larger)
      osdsPerDevice: "1" # this value can be overridden at the node or device level
##### ディレクトリを指定 #####
    directories:
    - path: /data
##### ノードを指定 #####
    nodes:
    - name: "vm1"
    - name: "vm3"
      directories:
      - path: "/data/storage-dir"

デプロイ後に各ノードのディレクトリを確認すると、vm1/datavm3では/data/storage-dirが利用されています。

## vm1

Every 2.0s: ls -l /data                                 Thu Jan 23 09:20:57 2020

total 24
drwx------ 2 root root 16384 Jan 12 12:39 lost+found
drwxr--r-- 4  167  167  4096 Jan 23 09:19 osd1
drwxr-xr-x 4 root root  4096 Jan 23 09:19 rook-ceph


## vm2

Every 2.0s: ls -l /data                                                 Thu Jan 23 09:21:08 2020

total 24
drwx------ 2 root root 16384 Jan 12 12:43 lost+found
drwxr-xr-x 3 root root  4096 Jan 23 09:17 mon-a
drwxr-xr-x 4 root root  4096 Jan 23 09:17 rook-ceph


## vm3

Every 2.0s: ls -l /data                                 Thu Jan 23 09:21:16 2020

total 24
drwx------ 2 root root 16384 Jan 12 12:45 lost+found
drwxr-xr-x 4 root root  4096 Jan 23 09:19 rook-ceph
drwxr-xr-x 3 root root  4096 Jan 23 09:19 storage-dir

[root@vm3 ~]# ls -l /data
total 24
drwx------ 2 root root 16384 Jan 12 12:45 lost+found
drwxr-xr-x 4 root root  4096 Jan 23 09:19 rook-ceph
drwxr-xr-x 3 root root  4096 Jan 23 09:19 storage-dir
[root@vm3 ~]# ls -l /data/storage-dir/
total 4
drwxr--r-- 4 167 167 4096 Jan 23 09:19 osd0
[root@vm3 ~]#

Storage Configuration: Cluster wide Devices

これは公式ドキュメントのサンプルにはありませんが、クラスター全体で特定のデバイスを利用する場合も載せておきます。

  • spec.storage.devices: 利用するデバイスを指定
    • name: デバイス名を指定("sda"など)
    • config: 特定のデバイス専用の設定
      • metadataDevice: OSDメタデータに利用するデバイスを指定
      • storeType: filestore bluestoreのいずれかを指定。ディレクトリを利用する場合、デフォルトではfilestoreが設定される
      • databaseSizeMB: bluestoreデータベースのサイズをMBで指定
      • walSizeMB: bluestore write-ahead log (WAL)のサイズをMBで指定
      • osdsPerDevice: 各デバイスで作成するOSD数を指定
      • encryptedDevice: trueの場合、dmcryptを利用してOSDボリュームを暗号化する。デフォルトではfalseに設定される

サンプル例

以下のyamlファイルでは、クラスター内の全てのノードについてsddバイスを利用するよう設定しています。

apiVersion: ceph.rook.io/v1
kind: CephCluster
metadata:
  name: rook-ceph
  namespace: rook-ceph
spec:
  cephVersion:
    image: ceph/ceph:v14.2.5
    allowUnsupported: true
  dataDirHostPath: /data
  skipUpgradeChecks: false
  continueUpgradeAfterChecksEvenIfNotHealthy: false
  mon:
    count: 1
    allowMultiplePerNode: true
  dashboard:
    enabled: true
    ssl: true
  storage:
    useAllNodes: true
    useAllDevices: false
    config:
      databaseSizeMB: "1024" # this value can be removed for environments with normal sized disks (100 GB or larger)
      journalSizeMB: "1024"  # this value can be removed for environments with normal sized disks (20 GB or larger)
      osdsPerDevice: "1" # this value can be overridden at the node or device level
##### デバイスを指定 #####
    devices:
    - name: "sdd"

上記ファイルをデプロイすると、クラスター内の全てのノードでOSDが作成されることが確認できます。各ノードを確認するとsddバイスを利用してボリュームが作成されていることが確認できるはずです。

[root@vm0 ceph]# kubectl get pods -n rook-ceph
NAME                                            READY   STATUS      RESTARTS   AGE
csi-cephfsplugin-6cg4g                          3/3     Running     0          3m10s
csi-cephfsplugin-mgxc9                          3/3     Running     0          3m10s
csi-cephfsplugin-provisioner-8b9d48896-fw8q2    4/4     Running     0          3m10s
csi-cephfsplugin-provisioner-8b9d48896-p2rxt    4/4     Running     0          3m10s
csi-cephfsplugin-wkjsq                          3/3     Running     0          3m10s
csi-rbdplugin-2dnw8                             3/3     Running     0          3m10s
csi-rbdplugin-882h7                             3/3     Running     0          3m10s
csi-rbdplugin-k6bvh                             3/3     Running     0          3m10s
csi-rbdplugin-provisioner-6d465d6c6f-k29bm      5/5     Running     0          3m10s
csi-rbdplugin-provisioner-6d465d6c6f-zgqvv      5/5     Running     0          3m10s
rook-ceph-crashcollector-vm1-87d7886d4-dswwf    1/1     Running     0          105s
rook-ceph-crashcollector-vm2-d9879bccc-v45r6    1/1     Running     0          2m54s
rook-ceph-crashcollector-vm3-5dddcf7994-z5vlq   1/1     Running     0          116s
rook-ceph-mgr-a-5997fc9dc8-hw6zq                1/1     Running     0          2m44s
rook-ceph-mon-a-8768cc588-nbxgf                 1/1     Running     0          2m54s
rook-ceph-operator-678887c8d-4zgrp              1/1     Running     0          3m25s
rook-ceph-osd-0-55dfb85d5b-hd8fh                1/1     Running     0          118s
rook-ceph-osd-1-75c8649dfb-rvx87                1/1     Running     0          116s
rook-ceph-osd-2-6bd69fdd7-wc8v4                 1/1     Running     0          105s
rook-ceph-osd-prepare-vm1-7gdjs                 0/1     Completed   0          2m23s
rook-ceph-osd-prepare-vm2-pvd9q                 0/1     Completed   0          2m23s
rook-ceph-osd-prepare-vm3-9wlmt                 0/1     Completed   0          2m23s
rook-ceph-tools-7f96779fb9-sfb2s                1/1     Running     0          2s
rook-discover-8m5np                             1/1     Running     0          3m23s
rook-discover-sbzmr                             1/1     Running     0          3m23s
rook-discover-wn65w                             1/1     Running     0          3m23s


# CRUSHマップを確認

[root@vm0 ceph]# kubectl exec -it rook-ceph-tools-7f96779fb9-sfb2s -n rook-ceph -- ceph osd tree
ID CLASS WEIGHT  TYPE NAME     STATUS REWEIGHT PRI-AFF
-1       0.18448 root default
-7       0.06149     host vm1
 2   hdd 0.06149         osd.2     up  1.00000 1.00000
-3       0.06149     host vm2
 0   hdd 0.06149         osd.0     up  1.00000 1.00000
-5       0.06149     host vm3
 1   hdd 0.06149         osd.1     up  1.00000 1.00000
[root@vm0 ceph]#

Node Affinity

Kubernetesの機能であるNode Affinity / Pod Affinity / Pod Anti-Affinity / Tolerationを利用し、OSD/MON/MGR Podを配置するノードを指定することができます。

  • spec.placement: Podをノードに配置するときのルールを指定
    • 対象のPodを指定(all mon mgr osd rbdmirrorのいずれか)
      • nodeAffinity: KubernetesのNode Affinityを利用
      • podAffinity: KubernetesのPod Affinityを利用
      • podAntiAffinity: KubernetesのPod Anti-Affinityを利用
      • tolerations: KubernetesのToleration機能を利用

※参考リンク:

Kubernetes Doc - Assigning Pods to Nodes

Kubernetes Doc - Taints and Tolerations

Node Affinityを利用する場合

以下のyamlファイルでは、nodeAffinityを利用し、全てのPodの配置場所をrole=storage-nodeというラベルが付与されたノードに限定します。

apiVersion: ceph.rook.io/v1
kind: CephCluster
metadata:
  name: rook-ceph
  namespace: rook-ceph
spec:
  cephVersion:
    image: ceph/ceph:v14.2.5
    allowUnsupported: true
  dataDirHostPath: /data
  skipUpgradeChecks: false
  continueUpgradeAfterChecksEvenIfNotHealthy: false
  mon:
    count: 1
    allowMultiplePerNode: true
  dashboard:
    enabled: true
    ssl: true
##### Node Affinityの条件を指定 #####
  placement:
    all:
      nodeAffinity:
        requiredDuringSchedulingIgnoredDuringExecution:
          nodeSelectorTerms:
          - matchExpressions:
            - key: role
              operator: In
              values:
              - storage-node
  storage:
    useAllNodes: true
    useAllDevices: false
    config:
      databaseSizeMB: "1024" # this value can be removed for environments with normal sized disks (100 GB or larger)
      journalSizeMB: "1024"  # this value can be removed for environments with normal sized disks (20 GB or larger)
      osdsPerDevice: "1" # this value can be overridden at the node or device level
    directories:
    - path: /data

vm1ノードにラベルを付与し、上記ファイルをデプロイした結果、vm1ノードにのみPodが配置されたことが確認できます。

# vm1にのみラベル付与
[root@vm0 ceph]# kubectl label node vm1 role=storage-node
node/vm1 labeled
[root@vm0 ceph]# kubectl get nodes --show-labels
NAME   STATUS   ROLES    AGE   VERSION   LABELS
vm0    Ready    master   10d   v1.17.0   beta.kubernetes.io/arch=amd64,beta.kubernetes.io/os=linux,kubernetes.io/arch=amd64,kubernetes.io/hostname=vm0,kubernetes.io/os=linux,node-role.kubernetes.io/master=
vm1    Ready    <none>   10d   v1.17.0   beta.kubernetes.io/arch=amd64,beta.kubernetes.io/os=linux,kubernetes.io/arch=amd64,kubernetes.io/hostname=vm1,kubernetes.io/os=linux,role=storage-node
vm2    Ready    <none>   10d   v1.17.0   beta.kubernetes.io/arch=amd64,beta.kubernetes.io/os=linux,kubernetes.io/arch=amd64,kubernetes.io/hostname=vm2,kubernetes.io/os=linux
vm3    Ready    <none>   10d   v1.17.0   beta.kubernetes.io/arch=amd64,beta.kubernetes.io/os=linux,kubernetes.io/arch=amd64,kubernetes.io/hostname=vm3,kubernetes.io/os=linux


# デプロイ後のPodの配置場所確認

[root@vm0 ceph]# kubectl get pods -n rook-ceph -o wide
NAME                                           READY   STATUS      RESTARTS   AGE     IP             NODE   NOMINATED NODE   READINESS GATES
csi-cephfsplugin-b8gn4                         3/3     Running     0          5m29s   10.0.1.7       vm2    <none>           <none>
csi-cephfsplugin-d9jqx                         3/3     Running     0          5m29s   10.0.1.5       vm1    <none>           <none>
csi-cephfsplugin-gxkjm                         3/3     Running     0          5m29s   10.0.1.4       vm3    <none>           <none>
csi-cephfsplugin-provisioner-8b9d48896-6l7k6   4/4     Running     0          5m29s   10.244.3.133   vm3    <none>           <none>
csi-cephfsplugin-provisioner-8b9d48896-mmkhv   4/4     Running     0          5m29s   10.244.2.137   vm2    <none>           <none>
csi-rbdplugin-cplr2                            3/3     Running     0          5m29s   10.0.1.7       vm2    <none>           <none>
csi-rbdplugin-gccsz                            3/3     Running     0          5m29s   10.0.1.4       vm3    <none>           <none>
csi-rbdplugin-provisioner-6d465d6c6f-9j2tn     5/5     Running     0          5m29s   10.244.3.132   vm3    <none>           <none>
csi-rbdplugin-provisioner-6d465d6c6f-jq24f     5/5     Running     0          5m29s   10.244.1.131   vm1    <none>           <none>
csi-rbdplugin-scrh8                            3/3     Running     0          5m29s   10.0.1.5       vm1    <none>           <none>
rook-ceph-crashcollector-vm1-87d7886d4-wff4g   1/1     Running     0          4m31s   10.244.1.140   vm1    <none>           <none>
rook-ceph-mgr-a-6df8b4b564-dhxpg               1/1     Running     0          5m3s    10.244.1.135   vm1    <none>           <none>
rook-ceph-mon-a-796676bcdb-952vd               1/1     Running     0          5m13s   10.244.1.134   vm1    <none>           <none>
rook-ceph-operator-678887c8d-djlxp             1/1     Running     1          28h     10.244.1.116   vm1    <none>           <none>
rook-ceph-osd-0-fb584798c-h7xlt                1/1     Running     0          4m31s   10.244.1.139   vm1    <none>           <none>
rook-ceph-osd-prepare-vm1-v7cxm                0/1     Completed   0          4m41s   10.244.1.138   vm1    <none>           <none>
rook-discover-f2fff                            1/1     Running     1          28h     10.244.1.115   vm1    <none>           <none>
rook-discover-p7hcr                            1/1     Running     1          28h     10.244.2.134   vm2    <none>           <none>
rook-discover-xjngr                            1/1     Running     1          28h     10.244.3.128   vm3    <none>           <none>


# 各ノードのディレクトリ

## vm1

Every 2.0s: ls -l /data                                 Fri Jan 24 06:41:25 2020

total 28
drwx------ 2 root root 16384 Jan 12 12:39 lost+found
drwxr-xr-x 3 root root  4096 Jan 24 06:33 mon-a
drwxr--r-- 4  167  167  4096 Jan 24 06:33 osd0
drwxr-xr-x 4 root root  4096 Jan 24 06:33 rook-ceph

## vm2

Every 2.0s: ls -l /data                                 Fri Jan 24 06:41:35 2020

total 16
drwx------ 2 root root 16384 Jan 12 12:43 lost+found

## vm3

Every 2.0s: ls -l /data                                 Fri Jan 24 06:41:47 2020

total 16
drwx------ 2 root root 16384 Jan 12 12:45 lost+found

Pod Affinityを利用する場合

以下のyamlファイルでは、podAffinityを利用し、全てのPodの配置場所をapp=sample-nginxというラベルが付与されたPodが存在するノードに限定します。

apiVersion: ceph.rook.io/v1
kind: CephCluster
metadata:
  name: rook-ceph
  namespace: rook-ceph
spec:
  cephVersion:
    image: ceph/ceph:v14.2.5
    allowUnsupported: true
  dataDirHostPath: /data
  skipUpgradeChecks: false
  continueUpgradeAfterChecksEvenIfNotHealthy: false
  mon:
    count: 1
    allowMultiplePerNode: true
  dashboard:
    enabled: true
    ssl: true
##### Pod Affinityの条件を指定 #####
  placement:
    all:
      podAffinity:
        requiredDuringSchedulingIgnoredDuringExecution:
        - labelSelector:
            matchExpressions:
            - key: app
              operator: In
              values:
              - sample-nginx
          topologyKey: kubernetes.io/hostname
  storage:
    useAllNodes: true
    useAllDevices: false
    config:
      databaseSizeMB: "1024" # this value can be removed for environments with normal sized disks (100 GB or larger)
      journalSizeMB: "1024"  # this value can be removed for environments with normal sized disks (20 GB or larger)
      osdsPerDevice: "1" # this value can be overridden at the node or device level
    directories:
    - path: /data

事前にテスト用Podを作成してから上記ファイルを利用してデプロイすると、テスト用Podの存在するノード上でしかOSD/MON/MGR Podが作成されないことが確認できます。また、一度スケジューリングされたPodは、テスト用Podを削除しても残り続けます。

# テスト用Podのyamlファイルの中身

[root@vm0 ceph]# cat cluster-test-podaffinity-pod.yaml
apiVersion: v1
kind: Pod
metadata:
  name: sample-nginx
  namespace: rook-ceph
  labels:
    app: sample-nginx
spec:
  containers:
  - image: nginx:1.12
    name: nginx-container
[root@vm0 ceph]# 


# デプロイ後の各Podの配置場所確認
[root@vm0 ceph]# kubectl get pods -n rook-ceph -o wide
NAME                                            READY   STATUS      RESTARTS   AGE     IP             NODE     NOMINATED NODE   READINESS GATES
csi-cephfsplugin-fgb42                          3/3     Running     0          2m7s    10.0.1.5       vm1      <none>           <none>
csi-cephfsplugin-lcxvv                          3/3     Running     0          2m7s    10.0.1.7       vm2      <none>           <none>
csi-cephfsplugin-provisioner-8b9d48896-fv4zq    4/4     Running     0          2m7s    10.244.2.161   vm2      <none>           <none>
csi-cephfsplugin-provisioner-8b9d48896-g8mg2    4/4     Running     0          2m7s    10.244.1.170   vm1      <none>           <none>
csi-cephfsplugin-t5f5b                          3/3     Running     0          2m7s    10.0.1.4       vm3      <none>           <none>
csi-rbdplugin-gs5r9                             3/3     Running     0          2m7s    10.0.1.7       vm2      <none>           <none>
csi-rbdplugin-l9gvp                             3/3     Running     0          2m7s    10.0.1.4       vm3      <none>           <none>
csi-rbdplugin-provisioner-6d465d6c6f-bllcp      5/5     Running     0          2m7s    10.244.3.159   vm3      <none>           <none>
csi-rbdplugin-provisioner-6d465d6c6f-rvj97      5/5     Running     0          2m7s    10.244.1.169   vm1      <none>           <none>
csi-rbdplugin-sqnjd                             3/3     Running     0          2m7s    10.0.1.5       vm1      <none>           <none>
rook-ceph-crashcollector-vm3-5dddcf7994-7f947   1/1     Running     0          62s     10.244.3.167   vm3      <none>           <none>
rook-ceph-mgr-a-78d8bd5c9b-5dwtb                1/1     Running     0          93s     10.244.3.163   vm3      <none>           <none>
rook-ceph-mon-a-66876c5579-nwbd7                1/1     Running     0          103s    10.244.3.162   vm3      <none>           <none>
rook-ceph-operator-678887c8d-djlxp              1/1     Running     2          32h     10.244.1.162   vm1      <none>           <none>
rook-ceph-osd-0-5859bcc4f5-q7j7r                1/1     Running     0          63s     10.244.3.166   vm3      <none>           <none>
rook-ceph-osd-prepare-vm1-kbg7k                 0/1     Pending     0          71s     <none>         <none>   <none>           <none>
rook-ceph-osd-prepare-vm2-8f44f                 0/1     Pending     0          71s     <none>         <none>   <none>           <none>
rook-ceph-osd-prepare-vm3-8zxmv                 0/1     Completed   0          71s     10.244.3.165   vm3      <none>           <none>
rook-discover-f2fff                             1/1     Running     2          32h     10.244.1.161   vm1      <none>           <none>
rook-discover-p7hcr                             1/1     Running     2          32h     10.244.2.152   vm2      <none>           <none>
rook-discover-xjngr                             1/1     Running     2          32h     10.244.3.152   vm3      <none>           <none>
sample-nginx                                    1/1     Running     0          6m49s   10.244.3.158   vm3      <none>           <none>


# 配置されなかったノード上のrook-ceph-osd-prepareでは、以下のようなログが確認できる

[root@vm0 ceph]# kubectl describe pods rook-ceph-osd-prepare-vm1-jk8zw -n rook-ceph

(中略)

Events:
  Type     Reason            Age                From               Message
  ----     ------            ----               ----               -------
  Warning  FailedScheduling  5s (x8 over 5m8s)  default-scheduler  0/4 nodes are available: 1 node(s) didn't match pod affinity rules, 3 node(s) didn't match node selector.
[root@vm0 ceph]# 


# テスト用Podを削除してもCeph関連Podの状態や配置は変わらない

[root@vm0 ceph]# kubectl delete -f cluster-test-podaffinity-pod.yaml
pod "sample-nginx" deleted

[root@vm0 ceph]# kubectl get pods -n rook-ceph
NAME                                            READY   STATUS      RESTARTS   AGE
csi-cephfsplugin-69nd7                          3/3     Running     0          8m48s
csi-cephfsplugin-h25vl                          3/3     Running     0          8m48s
csi-cephfsplugin-lv9l7                          3/3     Running     0          8m48s
csi-cephfsplugin-provisioner-8b9d48896-pzrk2    4/4     Running     0          8m48s
csi-cephfsplugin-provisioner-8b9d48896-tvgv7    4/4     Running     0          8m48s
csi-rbdplugin-27z2s                             3/3     Running     0          8m48s
csi-rbdplugin-provisioner-6d465d6c6f-qw7dx      5/5     Running     0          8m48s
csi-rbdplugin-provisioner-6d465d6c6f-r952z      5/5     Running     0          8m48s
csi-rbdplugin-rgpsm                             3/3     Running     0          8m48s
csi-rbdplugin-ts8mf                             3/3     Running     0          8m48s
rook-ceph-crashcollector-vm3-5dddcf7994-qwfrg   1/1     Running     0          7m49s
rook-ceph-mgr-a-549db98cf9-4qsrn                1/1     Running     0          8m19s
rook-ceph-mon-a-9cd785977-xm2s7                 1/1     Running     0          8m29s
rook-ceph-operator-678887c8d-djlxp              1/1     Running     3          35h
rook-ceph-osd-0-bfc6bcd7-hrxqj                  1/1     Running     0          7m49s
rook-ceph-osd-prepare-vm1-jk8zw                 0/1     Pending     0          7m58s
rook-ceph-osd-prepare-vm2-sjkg2                 0/1     Pending     0          7m58s
rook-ceph-osd-prepare-vm3-dhvhd                 0/1     Completed   0          7m57s
rook-discover-f2fff                             1/1     Running     3          35h
rook-discover-p7hcr                             1/1     Running     3          35h
rook-discover-xjngr                             1/1     Running     3          35h

Pod Anti-Affinityを利用する場合

以下のyamlファイルでは、podAntiAffinityを利用し、全てのPodの配置場所をapp=sample-nginxというラベルが付与されたPodが存在「しない」ノードに限定します。

apiVersion: ceph.rook.io/v1
kind: CephCluster
metadata:
  name: rook-ceph
  namespace: rook-ceph
spec:
  cephVersion:
    image: ceph/ceph:v14.2.5
    allowUnsupported: true
  dataDirHostPath: /data
  skipUpgradeChecks: false
  continueUpgradeAfterChecksEvenIfNotHealthy: false
  mon:
    count: 1
    allowMultiplePerNode: true
  dashboard:
    enabled: true
    ssl: true
##### Pod Anti-Affinityの条件を指定 #####
  placement:
    all:
      podAntiAffinity:
        requiredDuringSchedulingIgnoredDuringExecution:
        - labelSelector:
            matchExpressions:
            - key: app
              operator: In
              values:
              - sample-nginx
          topologyKey: kubernetes.io/hostname
  storage:
    useAllNodes: true
    useAllDevices: false
    config:
      databaseSizeMB: "1024" # this value can be removed for environments with normal sized disks (100 GB or larger)
      journalSizeMB: "1024"  # this value can be removed for environments with normal sized disks (20 GB or larger)
      osdsPerDevice: "1" # this value can be overridden at the node or device level
    directories:
    - path: /data

テスト用Podを作成したのちに上記ファイルをデプロイすると、テスト用Podの存在しないvm1 vm2にPodが作成されたことが確認できます。

[root@vm0 ceph]# kubectl get pods -n rook-ceph -o wide
NAME                                           READY   STATUS      RESTARTS   AGE     IP             NODE     NOMINATED NODE   READINESS GATES
csi-cephfsplugin-bcxfq                         3/3     Running     0          2m43s   10.0.1.4       vm3      <none>           <none>
csi-cephfsplugin-c2pqc                         3/3     Running     0          2m43s   10.0.1.7       vm2      <none>           <none>
csi-cephfsplugin-provisioner-8b9d48896-9zpgz   4/4     Running     0          2m43s   10.244.3.186   vm3      <none>           <none>
csi-cephfsplugin-provisioner-8b9d48896-wnlvk   4/4     Running     0          2m43s   10.244.2.167   vm2      <none>           <none>
csi-cephfsplugin-z5hnh                         3/3     Running     0          2m43s   10.0.1.5       vm1      <none>           <none>
csi-rbdplugin-9fcf4                            3/3     Running     0          2m43s   10.0.1.7       vm2      <none>           <none>
csi-rbdplugin-g28nk                            3/3     Running     0          2m43s   10.0.1.4       vm3      <none>           <none>
csi-rbdplugin-n2fwb                            3/3     Running     0          2m43s   10.0.1.5       vm1      <none>           <none>
csi-rbdplugin-provisioner-6d465d6c6f-66n2f     5/5     Running     0          2m43s   10.244.3.185   vm3      <none>           <none>
csi-rbdplugin-provisioner-6d465d6c6f-r24mv     5/5     Running     0          2m43s   10.244.1.176   vm1      <none>           <none>
rook-ceph-crashcollector-vm1-87d7886d4-2f9mz   1/1     Running     0          105s    10.244.1.181   vm1      <none>           <none>
rook-ceph-crashcollector-vm2-d9879bccc-hp7rk   1/1     Running     0          2m25s   10.244.2.171   vm2      <none>           <none>
rook-ceph-mgr-a-d4668d784-m9wm9                1/1     Running     0          2m15s   10.244.1.178   vm1      <none>           <none>
rook-ceph-mon-a-79b756c96b-gc7sx               1/1     Running     0          2m25s   10.244.2.170   vm2      <none>           <none>
rook-ceph-operator-678887c8d-djlxp             1/1     Running     4          35h     10.244.1.174   vm1      <none>           <none>
rook-ceph-osd-0-69f97947f9-trb5k               1/1     Running     0          106s    10.244.2.173   vm2      <none>           <none>
rook-ceph-osd-1-745484f4d6-cxq84               1/1     Running     0          105s    10.244.1.180   vm1      <none>           <none>
rook-ceph-osd-prepare-vm1-8tjth                0/1     Completed   0          115s    10.244.1.179   vm1      <none>           <none>
rook-ceph-osd-prepare-vm2-zpx2p                0/1     Completed   0          115s    10.244.2.172   vm2      <none>           <none>
rook-ceph-osd-prepare-vm3-xnz4p                0/1     Pending     0          115s    <none>         <none>   <none>           <none>
rook-discover-f2fff                            1/1     Running     4          35h     10.244.1.175   vm1      <none>           <none>
rook-discover-p7hcr                            1/1     Running     4          35h     10.244.2.165   vm2      <none>           <none>
rook-discover-xjngr                            1/1     Running     4          35h     10.244.3.184   vm3      <none>           <none>
sample-nginx                                   1/1     Running     1          12m     10.244.3.183   vm3      <none>           <none>
[root@vm0 ceph]#

Resource Requests/Limits

クラスター全体、あるいは特定のノード上のPodに対して、CPU・メモリリソースの制限を設定することができます。

※参考リンク:

Github - Rook/Rook: Managing Compute Resources for rook

Kubernetes Doc - Managing Compute Resources for Containers

  • spec.resources: クラスター全体に対するリソース制限を設定
    • 制御対象Pod: Rookコンポーネントmon mgr osd rbdmirror prepareosd crashcollectorから選択)
      • requests: 利用するリソースの下限を設定
        • cpu: CPU下限値
        • memory: メモリ下限値
      • limits: 利用するリソースの上限を設定
        • cpu: CPU上限値
        • memory: メモリ上限値
  • spec.storage.nodes.resources: 特定ノードに対するOSDのリソース制限を設定
    • requests: 利用するリソースの下限を設定
      • cpu: CPU下限値
      • memory: メモリ下限値
    • limits: 利用するリソースの上限を設定
      • cpu: CPU上限値
      • memory: メモリ上限値

OSD Topology

クラスターの保存するデータをfailureDomain間で散らせて配置するためには、クラスターのトポロジーを設定する必要があります。トポロジークラスター内のノードにラベルを付与することでコントロールすることができ、クラスターにOSDを初めてデプロイする際にラベルを検知してCRUSHマップに反映します。

storeType: bluestoreのみ利用可能

指定可能なラベルは以下の通りで、failure-domain.beta.kubernetes.io/regionからtopology.rook.io/chassisに向けた階層構造になります。

  • failure-domain.beta.kubernetes.io/region
  • failure-domain.beta.kubernetes.io/zone
  • topology.rook.io/datacenter
  • topology.rook.io/room
  • topology.rook.io/pod
  • topology.rook.io/pdu
  • topology.rook.io/row
  • topology.rook.io/rack
  • topology.rook.io/chassis

サンプル例

以下のyamlファイルは、クラスター全体にOSDを配置するよう設定しています。

apiVersion: ceph.rook.io/v1
kind: CephCluster
metadata:
  name: rook-ceph
  namespace: rook-ceph
spec:
  cephVersion:
    image: ceph/ceph:v14.2.5
    allowUnsupported: true
  dataDirHostPath: /data
  skipUpgradeChecks: false
  continueUpgradeAfterChecksEvenIfNotHealthy: false
  mon:
    count: 1
    allowMultiplePerNode: true
  dashboard:
    enabled: true
    ssl: true
  storage:
    useAllNodes: true
    useAllDevices: false
    config:
      databaseSizeMB: "1024" # this value can be removed for environments with normal sized disks (100 GB or larger)
      journalSizeMB: "1024"  # this value can be removed for environments with normal sized disks (20 GB or larger)
      osdsPerDevice: "1" # this value can be overridden at the node or device level
    devices:
    - name: "sdd"

上記ファイルをデプロイする前に、各ノードにラベルを付与します。今回はtopology.rook.io/datacenter topology.rook.io/rackの2つを付与し、以下のような構造となるよう設定します。

f:id:FY0323:20200129154809p:plain
OSD Topology設定図

CephClusteryamlファイルをデプロイし、CRUSHマップを確認すると、ラベル情報に基づいたトポロジーが設定されていることが確認できます。

# ノードのラベル確認
[root@vm0 ceph]# kubectl get nodes --show-labels
NAME   STATUS   ROLES    AGE   VERSION   LABELS
vm0    Ready    master   14d   v1.17.0   beta.kubernetes.io/arch=amd64,beta.kubernetes.io/os=linux,kubernetes.io/arch=amd64,kubernetes.io/hostname=vm0,kubernetes.io/os=linux,node-role.kubernetes.io/master=
vm1    Ready    <none>   14d   v1.17.0   beta.kubernetes.io/arch=amd64,beta.kubernetes.io/os=linux,kubernetes.io/arch=amd64,kubernetes.io/hostname=vm1,kubernetes.io/os=linux,topology.rook.io/datacenter=dc1,topology.rook.io/rack=rack1
vm2    Ready    <none>   14d   v1.17.0   beta.kubernetes.io/arch=amd64,beta.kubernetes.io/os=linux,kubernetes.io/arch=amd64,kubernetes.io/hostname=vm2,kubernetes.io/os=linux,topology.rook.io/datacenter=dc1,topology.rook.io/rack=rack2
vm3    Ready    <none>   14d   v1.17.0   beta.kubernetes.io/arch=amd64,beta.kubernetes.io/os=linux,kubernetes.io/arch=amd64,kubernetes.io/hostname=vm3,kubernetes.io/os=linux,topology.rook.io/datacenter=dc2,topology.rook.io/rack=rack3
[root@vm0 ceph]#


# CephClusterデプロイ後のOSD Podの配置確認

[root@vm0 ceph]# kubectl get pods -n rook-ceph -o wide
NAME                                            READY   STATUS      RESTARTS   AGE     IP             NODE   NOMINATED NODE   READINESS GATES
csi-cephfsplugin-56rf7                          3/3     Running     3          5h29m   10.0.1.7       vm2    <none>           <none>
csi-cephfsplugin-p5h9g                          3/3     Running     3          5h29m   10.0.1.4       vm3    <none>           <none>
csi-cephfsplugin-provisioner-8b9d48896-z47zw    4/4     Running     4          5h29m   10.244.2.103   vm2    <none>           <none>
csi-cephfsplugin-provisioner-8b9d48896-z5wgr    4/4     Running     4          5h29m   10.244.1.43    vm1    <none>           <none>
csi-cephfsplugin-qt9qn                          3/3     Running     3          5h29m   10.0.1.5       vm1    <none>           <none>
csi-rbdplugin-k22h8                             3/3     Running     3          5h29m   10.0.1.5       vm1    <none>           <none>
csi-rbdplugin-provisioner-6d465d6c6f-6qbbk      5/5     Running     5          5h29m   10.244.3.42    vm3    <none>           <none>
csi-rbdplugin-provisioner-6d465d6c6f-gt5hh      5/5     Running     5          5h29m   10.244.1.42    vm1    <none>           <none>
csi-rbdplugin-rb6bb                             3/3     Running     3          5h29m   10.0.1.4       vm3    <none>           <none>
csi-rbdplugin-xhq9z                             3/3     Running     3          5h29m   10.0.1.7       vm2    <none>           <none>
rook-ceph-crashcollector-vm1-87d7886d4-9xmhd    1/1     Running     1          5h27m   10.244.1.41    vm1    <none>           <none>
rook-ceph-crashcollector-vm2-d9879bccc-kwkfs    1/1     Running     1          5h28m   10.244.2.106   vm2    <none>           <none>
rook-ceph-crashcollector-vm3-5dddcf7994-5q8zz   1/1     Running     1          5h27m   10.244.3.41    vm3    <none>           <none>
rook-ceph-mgr-a-5d74c8b979-c688d                1/1     Running     1          5h28m   10.244.3.44    vm3    <none>           <none>
rook-ceph-mon-a-5744b55f44-66sm2                1/1     Running     1          5h28m   10.244.2.108   vm2    <none>           <none>
rook-ceph-operator-678887c8d-wqxj4              1/1     Running     1          5h30m   10.244.3.43    vm3    <none>           <none>
rook-ceph-osd-0-777554d77c-mn7lc                1/1     Running     1          5h27m   10.244.2.107   vm2    <none>           <none>
rook-ceph-osd-1-6d7bf57cd9-z44jb                1/1     Running     0          13m     10.244.3.48    vm3    <none>           <none>
rook-ceph-osd-2-65d7fb799-gznkz                 1/1     Running     0          13m     10.244.1.49    vm1    <none>           <none>
rook-ceph-osd-prepare-vm1-ghwhh                 0/1     Completed   0          14m     10.244.1.48    vm1    <none>           <none>
rook-ceph-osd-prepare-vm2-ngt7j                 0/1     Completed   0          14m     10.244.2.111   vm2    <none>           <none>
rook-ceph-osd-prepare-vm3-8r7mk                 0/1     Completed   0          14m     10.244.3.47    vm3    <none>           <none>
rook-ceph-tools-7f96779fb9-xxvms                1/1     Running     1          5h26m   10.244.2.109   vm2    <none>           <none>
rook-discover-9brwm                             1/1     Running     1          5h30m   10.244.3.39    vm3    <none>           <none>
rook-discover-cd68k                             1/1     Running     1          5h30m   10.244.1.44    vm1    <none>           <none>
rook-discover-h4f5s                             1/1     Running     1          5h30m   10.244.2.104   vm2    <none>           <none>
[root@vm0 ceph]#


# CRUSHマップの確認
[root@vm0 ceph]# kubectl exec -it rook-ceph-tools-7f96779fb9-xxvms -n rook-ceph -- ceph osd tree
ID  CLASS WEIGHT  TYPE NAME             STATUS REWEIGHT PRI-AFF
 -1       0.18448 root default
 -5       0.12299     datacenter dc1
-16       0.06149         rack rack1
-15       0.06149             host vm1
  2   hdd 0.06149                 osd.2     up  1.00000 1.00000
 -4       0.06149         rack rack2
 -3       0.06149             host vm2
  0   hdd 0.06149                 osd.0     up  1.00000 1.00000
-11       0.06149     datacenter dc2
-10       0.06149         rack rack3
 -9       0.06149             host vm3
  1   hdd 0.06149                 osd.1     up  1.00000 1.00000
[root@vm0 ceph]#

トポロジーを利用するにはCephBlockPoolspec.failureDomainで指定します。ここではdatacenterをfailureDomainに指定し、異なるデータセンターにレプリカが作成されるよう設定します。

apiVersion: ceph.rook.io/v1
kind: CephBlockPool
metadata:
  name: replicapool
  namespace: rook-ceph
spec:
##### failureDomainを指定 #####
  failureDomain: datacenter
  replicated:
    size: 2
---
apiVersion: storage.k8s.io/v1
kind: StorageClass
metadata:
   name: rook-ceph-block
provisioner: rook-ceph.rbd.csi.ceph.com
parameters:
    clusterID: rook-ceph
    pool: replicapool
    imageFormat: "2"
    imageFeatures: layering
    csi.storage.k8s.io/provisioner-secret-name: rook-csi-rbd-provisioner
    csi.storage.k8s.io/provisioner-secret-namespace: rook-ceph
    csi.storage.k8s.io/node-stage-secret-name: rook-csi-rbd-node
    csi.storage.k8s.io/node-stage-secret-namespace: rook-ceph
    csi.storage.k8s.io/fstype: ext4
reclaimPolicy: Delete

CephBlockPool StorageClassをデプロイし、クラスターに保存されたデータがどのOSDに対してレプリカを作成したかを確認します。

# CephBlockPool/StorageClassのデプロイ

[root@vm0 rbd]# kubectl apply -f storageclass-topology.yaml
cephblockpool.ceph.rook.io/replicapool created
storageclass.storage.k8s.io/rook-ceph-block created

[root@vm0 rbd]# kubectl get sc
NAME              PROVISIONER                  RECLAIMPOLICY   VOLUMEBINDINGMODE   ALLOWVOLUMEEXPANSION   AGE
rook-ceph-block   rook-ceph.rbd.csi.ceph.com   Delete          Immediate           false                  8s

[root@vm0 rbd]# kubectl get cephblockpool.ceph.rook.io -n rook-ceph
NAME          AGE
replicapool   32s


# テスト用Podのデプロイ
[root@vm0 kubernetes]# kubectl get pods
NAME                              READY   STATUS    RESTARTS   AGE
wordpress-mysql-b9ddd6d4c-8zx8x   1/1     Running   0          10m
[root@vm0 kubernetes]# kubectl get pvc
NAME             STATUS   VOLUME                                     CAPACITY   ACCESS MODES   STORAGECLASS      AGE
mysql-pv-claim   Bound    pvc-56c4157b-86dc-46e8-88e4-c9c0b5cb1254   1Gi        RWO            rook-ceph-block   10m
[root@vm0 kubernetes]# kubectl get svc
NAME              TYPE        CLUSTER-IP   EXTERNAL-IP   PORT(S)    AGE
kubernetes        ClusterIP   10.96.0.1    <none>        443/TCP    14d
wordpress-mysql   ClusterIP   None         <none>        3306/TCP   10m
[root@vm0 kubernetes]#


# レプリカの確認

[root@vm0 kubernetes]# kubectl -n rook-ceph exec -it rook-ceph-tools-7f96779fb9-xxvms -- ceph pg dump
dumped all
version 253
stamp 2020-01-28 13:04:57.946209
last_osdmap_epoch 0
last_pg_scan 0
PG_STAT OBJECTS MISSING_ON_PRIMARY DEGRADED MISPLACED UNFOUND BYTES    OMAP_BYTES* OMAP_KEYS* LOG DISK_LOG STATE        STATE_STAMP                VERSION REPORTED UP    UP_PRIMARY ACTING ACTING_PRIMARY LAST_SCRUB SCRUB_STAMP                LAST_DEEP_SCRUB DEEP_SCRUB_STAMP           SNAPTRIMQ_LEN
1.7           9                  0        0         0       0 30031872           0          0  12       12 active+clean 2020-01-28 13:01:44.045525   32'12    32:32 [0,1]          0  [0,1]              0        0'0 2020-01-28 13:00:05.797648             0'0 2020-01-28 13:00:05.797648             0
1.6           3                  0        0         0       0  8658944           0          0   5        5 active+clean 2020-01-28 13:01:44.055336    32'5    32:25 [2,1]          2  [2,1]              2        0'0 2020-01-28 13:00:05.797648             0'0 2020-01-28 13:00:05.797648             0
1.5           7                  0        0         0       0 25165824           0          0  32       32 active+clean 2020-01-28 13:01:44.055606   32'32    32:93 [2,1]          2  [2,1]              2        0'0 2020-01-28 13:00:05.797648             0'0 2020-01-28 13:00:05.797648             0
1.4           8                  0        0         0       0 25165840           0          0  37       37 active+clean 2020-01-28 13:01:44.053455   32'37    32:60 [1,0]          1  [1,0]              1        0'0 2020-01-28 13:00:05.797648             0'0 2020-01-28 13:00:05.797648             0
1.0           1                  0        0         0       0  4194304           0          0   3        3 active+clean 2020-01-28 13:01:44.055679    32'3    32:23 [2,1]          2  [2,1]              2        0'0 2020-01-28 13:00:05.797648             0'0 2020-01-28 13:00:05.797648             0
1.1           4                  0        0         0       0 12582912           0          0  32       32 active+clean 2020-01-28 13:01:44.055440   32'32    32:52 [2,1]          2  [2,1]              2        0'0 2020-01-28 13:00:05.797648             0'0 2020-01-28 13:00:05.797648             0
1.2           7                  0        0         0       0 17584147           0          0 382      382 active+clean 2020-01-28 13:01:44.055069  32'382   32:405 [2,1]          2  [2,1]              2        0'0 2020-01-28 13:00:05.797648             0'0 2020-01-28 13:00:05.797648             0
1.3           9                  0        0         0       0 24068096           0          0  89       89 active+clean 2020-01-28 13:01:44.045558   32'89   32:205 [0,1]          0  [0,1]              0        0'0 2020-01-28 13:00:05.797648             0'0 2020-01-28 13:00:05.797648             0

1 48 0 0 0 0 147451939 0 0 592 592

sum 48 0 0 0 0 147451939 0 0 592 592
OSD_STAT USED    AVAIL   USED_RAW TOTAL   HB_PEERS PG_SUM PRIMARY_PG_SUM
2         70 MiB  62 GiB  1.1 GiB  63 GiB    [0,1]      5              5
1        141 MiB  62 GiB  1.1 GiB  63 GiB    [0,2]      8              1
0         76 MiB  62 GiB  1.1 GiB  63 GiB    [1,2]      3              2
sum      286 MiB 186 GiB  3.3 GiB 189 GiB

* NOTE: Omap statistics are gathered during deep scrub and may be inaccurate soon afterwards depending on utilisation. See http://docs.ceph.com/docs/master/dev/placement-group/#omap-statistics for further details.

UP ACTINGの項目を見ると[0,1] [1,2]という値だけが確認できます。この数字はOSDの番号を表し、ここではOSD_0 OSD_1OSD_1 OSD_2がそれぞれペアになっているのがわかります。CRUSHマップを確認した結果からOSD_1OSD_0 OSD_2は別のdatacenterに配置しているため、作成したPoolでは別々のdatacenter間でレプリカを作成していることがわかります。

f:id:FY0323:20200129154832p:plain
OSD配置とfailureDomain

Using PVC storage for monitors

MON PodをPVC経由で作成することができます。

  • spec.mon
    • count: MON Podの数を指定
    • allowMultiplePerNode: tureの場合、1ノードに複数のMon Podを配置することを許可する
    • volumeClaimTemplate: KubernetesのStatefulSetで指定するvolumeClaimTemplatesのように、storageClassNameresources.requests.storageを指定する

※参考リンク:

Kubernetes Doc - StatefulSet

以下のファイルでは、あらかじめ用意したlocal-storageというStorageClassを利用してMON Podを3つ作成するよう指定しています。

apiVersion: ceph.rook.io/v1
kind: CephCluster
metadata:
  name: rook-ceph
  namespace: rook-ceph
spec:
  cephVersion:
    image: ceph/ceph:v14.2.5
    allowUnsupported: true
  dataDirHostPath: /data
  skipUpgradeChecks: false
  continueUpgradeAfterChecksEvenIfNotHealthy: false
##### MON Podの設定 #####
  mon:
    count: 3
    allowMultiplePerNode: false
    volumeClaimTemplate:
      spec:
        storageClassName: local-storage
        resources:
          requests:
            storage: 1Gi
  dashboard:
    enabled: true
    ssl: true
  storage:
    useAllNodes: true
    useAllDevices: false
    config:
      databaseSizeMB: "1024" # this value can be removed for environments with normal sized disks (100 GB or larger)
      journalSizeMB: "1024"  # this value can be removed for environments with normal sized disks (20 GB or larger)
      osdsPerDevice: "1" # this value can be overridden at the node or device level
    directories:
    - path: /data

Using StorageClassDeviceSets

Rook v1.1から導入されたOSD on PVCを実現する機能です。既に別の記事で試したことがあるので、詳細はそちらを参照してください。

  • spec.storage.storageClassDeviceSets: OSD on PVCを作成するために使用
    • name: set名
    • count: set内のデバイス
    • resources: デバイスのCPU/RAMのrequest/limitを設定
    • placement: デバイスの配置基準、nodeAffinity podAffinity podAntiAffinity
    • portable: trueにすると、failover時に別のノード間でOSDが移動することを許可する
    • tuneSlowDeviceClass: trueにすると、デバイスがSlow Deviceと識別された場合、Slow Device用にOSDが調整される
    • volumeClaimTemplates: spec.monと同様
      • volumeMode: PVC用に設定するvolumeモード、Blockが推奨
      • accessMode: PVC用に設定するaccessモードを指定
apiVersion: ceph.rook.io/v1
kind: CephCluster
metadata:
  name: rook-ceph
  namespace: rook-ceph
spec:
  dataDirHostPath: /var/lib/rook
##### MON Podの設定 #####
  mon:
    count: 3
    allowMultiplePerNode: false
    volumeClaimTemplate:
      spec:
        storageClassName: default
        resources:
          requests:
            storage: 10Gi
  cephVersion:
    image: ceph/ceph:v14.2.4-20190917
    allowUnsupported: false
  dashboard:
    enabled: true
    ssl: true
  network:
    hostNetwork: false
  storage:
##### Storage Class Device Setsの指定 #####
    storageClassDeviceSets:
    - name: set1
      count: 3
      portable: true
      placement:
        podAntiAffinity:
          preferredDuringSchedulingIgnoredDuringExecution:
          - weight: 100
            podAffinityTerm:
              labelSelector:
                matchExpressions:
                - key: app
                  operator: In
                  values:
                  - rook-ceph-osd
                - key: app
                  operator: In
                  values:
                  - rook-ceph-osd-prepare
              topologyKey: kubernetes.io/hostname
      resources:
      volumeClaimTemplates:
      - metadata:
          name: data
        spec:
          resources:
            requests:
              storage: 10Gi
          storageClassName: default
          volumeMode: Block
          accessModes:
            - ReadWriteOnce
  disruptionManagement:
    managePodBudgets: false
    osdMaintenanceTimeout: 30
    manageMachineDisruptionBudgets: false
    machineDisruptionBudgetNamespace: openshift-machine-api

その他

External cluster

サンプルではほかにもExternal Clusterの利用方法が紹介されています。

ストレージを利用するクライアントが存在するクラスター(local cluster)内だけでは足りず、別のクラスター(external cluster)のCephストレージを利用する必要があるケースが存在します。

  1. Kubernetesクラスターが複数存在し、それらが単一のCephクラスターを利用する場合
  2. Kubernetes環境外でCephクラスターを既に持っている場合
  3. Kubernetesクラスターと完全に独立したストレージ環境を必要とする場合

Rookでは、local cluster側にExternal clusterの情報を設定することで、別のクラスターにあるストレージリソースを利用することができます。

※参考リンク:

Github - Rook/Rook: Rook and External Ceph Clusters

MGR

Ceph MGRデーモンで利用するモジュールを指定できます。ドキュメント中ではpg_autoscalerというモジュールが紹介されています。

apiVersion: ceph.rook.io/v1
kind: CephCluster

(中略)

  mgr:
    modules:
    # Several modules should not need to be included in this list. The "dashboard" and "monitoring" modules
    # are already enabled by other settings in the cluster CR and the "rook" module is always enabled.
    - name: pg_autoscaler
      enabled: true

※参考リンク:

Ceph Doc - CEPH MANAGER DAEMON

Annotations

Rookコンポーネントalll mgr mon osd rbdmirror)に対してアノテーションを付与することができます。

apiVersion: ceph.rook.io/v1
kind: CephCluster

(中略)

  annotations:
    all: "test"
    mon: "Ceph Monitor"
    osd: "Ceph OSD"
# If no mgr annotations are set, prometheus scrape annotations will be set by default.
   mgr: "Ceph manager"

※参考リンク:

Kubernetes Doc - Annotations

Priority Class Name

Rookコンポーネントalll mgr mon osd rbdmirror)に対してPriorityClassNameを付与することができます。KubernetesではあらかじめPriority値を指定したPriorityClassリソースを用意し、Podデプロイ時に対象のPriorityClassの名前を指定することで、ノードのリソースが不足した際に削除されるPodの優先順位を設定することができます。RookコンポーネントPriorityClassを適用することで、リソース不足時などの状況でもRook関連のPodがダウンしないよう設定することができます。

apiVersion: ceph.rook.io/v1
kind: CephCluster

(中略)

  priorityClassNames:
    all: rook-ceph-default-priority-class
    mon: rook-ceph-mon-priority-class
    osd: rook-ceph-osd-priority-class
    mgr: rook-ceph-mgr-priority-class

※参考リンク:

Kubernetes Doc - Pod Priority and Preemption #PriorityClass

Ceph Block Pool CRD

CephBlockPoolリソースで設定可能な項目も載せておきます。

  • spec.failureDomain: データ複製時のfailureDomainを指定。host osdのほか、ノードに付与されたラベルも指定できる(利用可能なラベルはこちらを参照
  • spec.replicated: データ冗長化方式をreplicatedにする場合に利用
    • size: データ複製数を指定
  • spec.erasureCoded: データ複製方式をErasure Codeにする場合の設定項目を指定。OSDstoreTypebluestoreの場合のみ利用可能
    • dataChunks: 元のオブジェクトデータをいくつのチャンクに分割するかを指定
    • codingChunks: 復旧用のチャンクをいくつ作成するかを指定
  • spec.deviceClass: 特定のデバイスのみ(hddなど)にデータを配置するようCRUSHルールを設定する場合に利用
  • spec.crushRoot: プールに利用されるCRUSHマップのRootを指定

以下のようにyamlファイルで指定します。

apiVersion: ceph.rook.io/v1
kind: CephBlockPool
metadata:
  name: replicapool
  namespace: rook-ceph
spec:
  failureDomain: host
##### Erasure Codeを指定 #####
  erasureCoded:
    dataChunks: 2
    codingChunks: 1
---
apiVersion: storage.k8s.io/v1
kind: StorageClass
metadata:
   name: rook-ceph-block
provisioner: rook-ceph.rbd.csi.ceph.com
parameters:
    clusterID: rook-ceph
    pool: replicapool
    imageFormat: "2"
    imageFeatures: layering
    csi.storage.k8s.io/provisioner-secret-name: rook-csi-rbd-provisioner
    csi.storage.k8s.io/provisioner-secret-namespace: rook-ceph
    csi.storage.k8s.io/node-stage-secret-name: rook-csi-rbd-node
    csi.storage.k8s.io/node-stage-secret-namespace: rook-ceph
    csi.storage.k8s.io/fstype: ext4
reclaimPolicy: Delete

上記ファイルをデプロイし、結果を確認します。

[root@vm0 rbd]# kubectl apply -f storageclass-ec.yaml
cephblockpool.ceph.rook.io/replicapool created
storageclass.storage.k8s.io/rook-ceph-block created

[root@vm0 rbd]# kubectl get sc
NAME              PROVISIONER                  RECLAIMPOLICY   VOLUMEBINDINGMODE   ALLOWVOLUMEEXPANSION   AGE
rook-ceph-block   rook-ceph.rbd.csi.ceph.com   Delete          Immediate           false                  4s

[root@vm0 rbd]# kubectl get cephblockpool.ceph.rook.io -n rook-ceph
NAME          AGE
replicapool   25s
[root@vm0 rbd]#

toolbox Podから各種cephコマンドを実行し、結果を確認します。

# ceph osd lspoolsコマンド

[root@vm0 ceph]# kubectl exec -it rook-ceph-tools-7f96779fb9-6zt9k -n rook-ceph -- ceph osd lspools
7 replicapool


# rados dfコマンド

[root@vm0 ceph]# kubectl exec -it rook-ceph-tools-7f96779fb9-6zt9k -n rook-ceph -- rados df
POOL_NAME   USED OBJECTS CLONES COPIES MISSING_ON_PRIMARY UNFOUND DEGRADED RD_OPS  RD WR_OPS  WR USED COMPR UNDER COMPR
replicapool  0 B       0      0      0                  0       0        0      0 0 B      0 0 B        0 B         0 B

total_objects    0
total_used       3.0 GiB
total_avail      186 GiB
total_space      189 GiB


# ceph osd dumpコマンド

[root@vm0 ceph]# kubectl exec -it rook-ceph-tools-7f96779fb9-6zt9k -n rook-ceph -- ceph osd dump
epoch 78
fsid 5367b9be-67d2-4147-8905-461fa05392ff
created 2020-02-01 05:08:34.374372
modified 2020-02-01 17:19:35.256121
flags sortbitwise,recovery_deletes,purged_snapdirs,pglog_hardlimit
crush_version 19
full_ratio 0.95
backfillfull_ratio 0.9
nearfull_ratio 0.85
require_min_compat_client jewel
min_compat_client jewel
require_osd_release nautilus
pool 7 'replicapool' erasure size 3 min_size 2 crush_rule 1 object_hash rjenkins pg_num 8 pgp_num 8 autoscale_mode warn last_change 78 flags hashpspool,ec_overwrites stripe_width 8192 application rbd
max_osd 3
osd.0 up   in  weight 1 up_from 7 up_thru 76 down_at 0 last_clean_interval [0,0) [v2:10.244.2.177:6800/29390,v1:10.244.2.177:6801/29390] [v2:10.244.2.177:6802/29390,v1:10.244.2.177:6803/29390] exists,up 9e6178b9-b33e-42ac-812a-3a38d56ffd93
osd.1 up   in  weight 1 up_from 10 up_thru 76 down_at 0 last_clean_interval [0,0) [v2:10.244.1.93:6800/30924,v1:10.244.1.93:6801/30924] [v2:10.244.1.93:6802/30924,v1:10.244.1.93:6803/30924] exists,up 77692223-8413-4edd-8649-74251b6096e8
osd.2 up   in  weight 1 up_from 11 up_thru 76 down_at 0 last_clean_interval [0,0) [v2:10.244.3.91:6800/58716,v1:10.244.3.91:6801/58716] [v2:10.244.3.91:6802/58716,v1:10.244.3.91:6803/58716] exists,up b6765454-28bc-4de7-abf3-74e93d1be447


# ceph osd erasure-code-profile lsコマンド

[root@vm0 ceph]# kubectl exec -it rook-ceph-tools-7f96779fb9-6zt9k -n rook-ceph -- ceph osd erasure-code-profile ls
default
replicapool_ecprofile



# ceph osd erasure-code-profile getコマンド

[root@vm0 ceph]# kubectl exec -it rook-ceph-tools-7f96779fb9-6zt9k -n rook-ceph -- ceph osd erasure-code-profile get replicapool_ecprofile
crush-device-class=
crush-failure-domain=osd
crush-root=default
jerasure-per-chunk-alignment=false
k=2
m=1
plugin=jerasure
technique=reed_sol_van
w=8

参考ドキュメント

Rook Doc - Block Storage

Rook Doc - Ceph Cluster CRD

Rook Doc - Ceph Block Pool CRD