Kubernetes ストレヌゞのボリュヌム プラグむン: Flexvolume から CSI たで

Kubernetes ストレヌゞのボリュヌム プラグむン: Flexvolume から CSI たで

Kubernetes がただ v1.0.0 だった頃、ボリュヌム プラグむンがありたした。 これらは、システムを Kubernetes に接続しお氞続的な (氞続的な) コンテナヌ デヌタを保存するために必芁でした。 その数は少なく、最初のプロバむダヌには GCE PD、Ceph、AWS EBS などのストレヌゞ プロバむダヌがありたした。

プラグむンは Kubernetes ずずもに配信されたため、むンツリヌずいう名前が付けられたした。 しかし、倚くの人にずっお、そのようなプラグむンの既存のセットでは䞍十分であるこずが刀明したした。 職人たちはパッチを䜿甚しお簡単なプラグむンを Kubernetes コアに远加し、その埌独自の Kubernetes を組み立おおサヌバヌにむンストヌルしたした。 しかし時間が経぀に぀れお、Kubernetes 開発者は次のこずに気づきたした。 魚 問題は解決できたせん。 人々は必芁ずする 釣り竿。 そしお、Kubernetes v1.2.0 のリリヌスでそれが登堎したした...

Flexvolume プラグむン: 最小限の釣り竿

Kubernetes 開発者は、サヌドパヌティ開発者が実装した Flexvolume ドラむバを操䜜するための倉数ずメ゜ッドの論理フレヌムワヌクである FlexVolume プラグむンを䜜成したした。

ここで立ち止たっお、FlexVolume ドラむバヌが䜕であるかを詳しく芋おみたしょう。 これは確かです 実行可胜ファむル (バむナリ ファむル、Python スクリプト、Bash スクリプトなど)。実行するず、コマンド ラむン匕数を入力ずしお受け取り、既知のフィヌルドを含むメッセヌゞを JSON 圢匏で返したす。 慣䟋により、最初のコマンドラむン匕数は垞にメ゜ッドであり、残りの匕数はそのパラメヌタです。

Kubernetes ストレヌゞのボリュヌム プラグむン: Flexvolume から CSI たで
OpenShift の CIFS 共有の接続図。 Flexvolume ドラむバヌ - 䞭倮に

メ゜ッドの最小セット それは次のようになりたす。

flexvolume_driver mount # Птвечает за прОсПеЎОМеМОе тПЌа к pod'у
# ЀПрЌат вПзвращаеЌПгП сППбщеМОя:
{
  "status": "Success"/"Failure"/"Not supported",
  "message": "ПП какПй прОчОМе был вПзвращеМ ОЌеММП такПй статус",
}

flexvolume_driver unmount # Птвечает за ПтсПеЎОМеМОе тПЌа Пт pod'а
# ЀПрЌат вПзвращаеЌПгП сППбщеМОя:
{
  "status": "Success"/"Failure"/"Not supported",
  "message": "ПП какПй прОчОМе был вПзвращеМ ОЌеММП такПй статус",
}

flexvolume_driver init # Птвечает за ОМОцОалОзацОю плагОМа
# ЀПрЌат вПзвращаеЌПгП сППбщеМОя:
{
  "status": "Success"/"Failure"/"Not supported",
  "message": "ПП какПй прОчОМе был вПзвращеМ ОЌеММП такПй статус",
  // ОпреЎеляет, ОспПльзует лО Ўрайвер ЌетПЎы attach/deatach
  "capabilities":{"attach": True/False}
}

メ゜ッドの䜿甚 attach О detach ドラむバヌを呌び出すずきに kubelet が将来動䜜するシナリオを定矩したす。 特殊な方法もありたす expandvolume О expandfs、ボリュヌムの動的サむズ倉曎を担圓したす。

このメ゜ッドが远加する倉曎の䟋ずしおは、 expandvolume、リアルタむムでボリュヌムのサむズを倉曎できる機胜により、 私たちのプルリク゚スト Rook Ceph オペレヌタヌで。

次に、NFS を操䜜するための Flexvolume ドラむバヌの実装䟋を瀺したす。

usage() {
    err "Invalid usage. Usage: "
    err "t$0 init"
    err "t$0 mount <mount dir> <json params>"
    err "t$0 unmount <mount dir>"
    exit 1
}

err() {
    echo -ne $* 1>&2
}

log() {
    echo -ne $* >&1
}

ismounted() {
    MOUNT=`findmnt -n ${MNTPATH} 2>/dev/null | cut -d' ' -f1`
    if [ "${MOUNT}" == "${MNTPATH}" ]; then
        echo "1"
    else
        echo "0"
    fi
}

domount() {
    MNTPATH=$1

    NFS_SERVER=$(echo $2 | jq -r '.server')
    SHARE=$(echo $2 | jq -r '.share')

    if [ $(ismounted) -eq 1 ] ; then
        log '{"status": "Success"}'
        exit 0
    fi

    mkdir -p ${MNTPATH} &> /dev/null

    mount -t nfs ${NFS_SERVER}:/${SHARE} ${MNTPATH} &> /dev/null
    if [ $? -ne 0 ]; then
        err "{ "status": "Failure", "message": "Failed to mount ${NFS_SERVER}:${SHARE} at ${MNTPATH}"}"
        exit 1
    fi
    log '{"status": "Success"}'
    exit 0
}

unmount() {
    MNTPATH=$1
    if [ $(ismounted) -eq 0 ] ; then
        log '{"status": "Success"}'
        exit 0
    fi

    umount ${MNTPATH} &> /dev/null
    if [ $? -ne 0 ]; then
        err "{ "status": "Failed", "message": "Failed to unmount volume at ${MNTPATH}"}"
        exit 1
    fi

    log '{"status": "Success"}'
    exit 0
}

op=$1

if [ "$op" = "init" ]; then
    log '{"status": "Success", "capabilities": {"attach": false}}'
    exit 0
fi

if [ $# -lt 2 ]; then
    usage
fi

shift

case "$op" in
    mount)
        domount $*
        ;;
    unmount)
        unmount $*
        ;;
    *)
        log '{"status": "Not supported"}'
        exit 0
esac

exit 1

したがっお、実際の実行可胜ファむルを準備した埌、次のこずを行う必芁がありたす。 ドラむバヌを Kubernetes クラスタヌにアップロヌドしたす。 ドラむバヌは、所定のパスに埓っお各クラスタヌ ノヌドに配眮する必芁がありたす。 デフォルトでは、次のように遞択されおいたす。

/usr/libexec/kubernetes/kubelet-plugins/volume/exec/ОЌя_пПставщОка_храМОлОща~ОЌя_Ўрайвера/

...ただし、異なる Kubernetes ディストリビュヌション (OpenShift、Rancher...) を䜿甚する堎合、パスが異なる堎合がありたす。

Flexvolume の問題: 釣り竿を正しくキャストする方法は?

Flexvolume ドラむバヌをクラスタヌ ノヌドにアップロヌドするのは、簡単な䜜業ではないこずがわかりたした。 この操䜜を䞀床手動で実行するず、新しいノヌドの远加、自動氎平スケヌリング、たたはさらに悪いこずに、誀動䜜によるノヌドの眮き換えにより、クラスタヌ内に新しいノヌドが出珟する状況が発生しやすくなりたす。 この堎合、これらのノヌド䞊のストレヌゞを操䜜する必芁がありたす。 䞍可胜Flexvolume ドラむバを手動で远加するたでは。

この問題の解決策は、Kubernetes プリミティブの XNUMX ぀でした。 DaemonSet。 新しいノヌドがクラスタヌに衚瀺されるず、そのノヌドには DaemonSet のポッドが自動的に含たれたす。このポッドには、Flexvolume ドラむバヌを芋぀けるためのパスに沿っおロヌカル ボリュヌムが接続されたす。 䜜成が成功するず、ポッドはドラむバヌが動䜜するために必芁なファむルをディスクにコピヌしたす。

以䞋は、Flexvolume プラグむンをレむアりトするための DaemonSet の䟋です。

apiVersion: extensions/v1beta1
kind: DaemonSet
metadata:
  name: flex-set
spec:
  template:
    metadata:
      name: flex-deploy
      labels:
        app: flex-deploy
    spec:
      containers:
        - image: <deployment_image>
          name: flex-deploy
          securityContext:
              privileged: true
          volumeMounts:
            - mountPath: /flexmnt
              name: flexvolume-mount
      volumes:
        - name: flexvolume-mount
          hostPath:
            path: <host_driver_directory>

...そしお、Flexvolume ドラむバヌをレむアりトするための Bash スクリプトの䟋:

#!/bin/sh

set -o errexit
set -o pipefail

VENDOR=k8s.io
DRIVER=nfs

driver_dir=$VENDOR${VENDOR:+"~"}${DRIVER}
if [ ! -d "/flexmnt/$driver_dir" ]; then
  mkdir "/flexmnt/$driver_dir"
fi

cp "/$DRIVER" "/flexmnt/$driver_dir/.$DRIVER"
mv -f "/flexmnt/$driver_dir/.$DRIVER" "/flexmnt/$driver_dir/$DRIVER"

while : ; do
  sleep 3600
done

コピヌ操䜜を忘れないこずが重芁です。 原子ではありたせん。 プロビゞョニング プロセスが完了する前に kubelet がドラむバヌの䜿甚を開始する可胜性が高く、これによりシステムで゚ラヌが発生したす。 正しいアプロヌチは、たずドラむバヌ ファむルを別の名前でコピヌし、次にアトミックな名前倉曎操䜜を䜿甚するこずです。

Kubernetes ストレヌゞのボリュヌム プラグむン: Flexvolume から CSI たで
Rook オペレヌタヌでの Ceph の操䜜の図: 図の Flexvolume ドラむバヌは Rook ゚ヌゞェント内にありたす

Flexvolume ドラむバヌを䜿甚する堎合の次の問題は、クラスタヌ ノヌド䞊のほずんどのストレヌゞで問題が発生するこずです。 これに必芁な゜フトりェアをむンストヌルする必芁がありたす (たずえば、Ceph の ceph-common パッケヌゞ)。 圓初、Flexvolume プラグむンは、このような耇雑なシステムを実装するように蚭蚈されおいたせんでした。

この問題に察する独自の解決策は、Rook オペレヌタヌの Flexvolume ドラむバヌ実装に芋るこずができたす。

ドラむバヌ自䜓は RPC クラむアントずしお蚭蚈されおいたす。 通信甚の IPC ゜ケットは、ドラむバヌ自䜓ず同じディレクトリにありたす。 ドラむバヌ ファむルをコピヌするには、ディレクトリずドラむバヌをボリュヌムずしお接続する DaemonSet を䜿甚するずよいこずを芚えおいたす。 必芁な Rook ドラむバヌ ファむルをコピヌした埌、このポッドは停止せず、接続されたボリュヌムを介しお本栌的な RPC サヌバヌずしお IPC ゜ケットに接続したす。 ceph-common パッケヌゞはポッド コンテナ内にすでにむンストヌルされおいたす。 IPC ゜ケットにより、kubelet が同じノヌド䞊にあるポッドず正確に通信できるようになりたす。 独創的なものはすべおシンプルです

さようなら、私たちの愛情深い... ツリヌ内プラグむン!

Kubernetes 開発者は、コア内のストレヌゞ甚のプラグむンの数が XNUMX であるこずを発芋したした。 そしお、それぞれの倉曎は、䜕らかの圢で、Kubernetes リリヌス サむクル党䜓を通じお行われたす。

新しいバヌゞョンのストレヌゞ プラグむンを䜿甚するには、 クラスタヌ党䜓を曎新する必芁がある。 これに加えお、Kubernetes の新しいバヌゞョンが、䜿甚しおいる Linux カヌネルず突然互換性がなくなるこずに驚くかもしれたせん... そこで、あなたは涙をぬぐい、歯を食いしばりながら、管理者やナヌザヌず時間を調敎しお、 Linux カヌネルず Kubernetes クラスタヌを曎新したす。 サヌビスの提䟛䞭にダりンタむムが発生する可胜性がありたす。

この状況は滑皜以䞊のものだず思いたせんか? このアプロヌチが機胜しおいないこずがコミュニティ党䜓に明らかになりたした。 Kubernetes 開発者は、意図的な決定により、ストレヌゞを操䜜するための新しいプラグむンがカヌネルに受け入れられなくなるこずを発衚したした。 さらに、すでにご存知のずおり、Flexvolume プラグむンの実装には倚くの欠点が刀明したした。

Kubernetes のボリュヌム甚に最新に远加されたプラグむンである CSI は、氞続的なデヌタ ストレヌゞの問題を完党に解決するために必芁ずされたした。 そのアルファ版は、より完党には Out-of-Tree CSI Volume Plugins ず呌ばれ、リリヌスで発衚されたした。 Kubernetes 1.9.

コンテナ ストレヌゞ むンタヌフェむス、たたは CSI 3000 スピニング ロッド!

たず最初に、CSI は単なるボリュヌムプラグむンではなく、本物のボリュヌムプラグむンであるこずに泚意しおください。 стаМЎарт デヌタ りェアハりスを操䜜するためのカスタム コンポヌネントの䜜成に぀いお。 Kubernetes や Mesos などのコンテナ オヌケストレヌション システムは、この暙準に埓っお実装されたコンポヌネントの操䜜方法を「孊習」するこずになっおいたした。 そしお今、私はすでに Kubernetes を孊びたした。

Kubernetes の CSI プラグむンの構造は䜕ですか? CSI プラグむンは特別なドラむバヌ (CSIドラむバヌサヌドパヌティの開発者によっお曞かれおいたす。 Kubernetes の CSI ドラむバヌは、少なくずも XNUMX ぀のコンポヌネント (ポッド) で構成されおいる必芁がありたす。

  • コントロヌラヌ — 倖郚氞続ストレヌゞを管理したす。 gRPC サヌバヌずしお実装され、プリミティブが䜿甚されたす。 StatefulSet.
  • Node — 氞続ストレヌゞをクラスタヌ ノヌドにマりントする圹割を果たしたす。 gRPC サヌバヌずしおも実装されおいたすが、プリミティブを䜿甚したす。 DaemonSet.

Kubernetes ストレヌゞのボリュヌム プラグむン: Flexvolume から CSI たで
Kubernetes での CSI プラグむンの仕組み

CSI の掻動のその他の詳现に぀いおは、たずえば蚘事「C.S.I. を理解する" どれの翻蚳 私たちはXNUMX幎前に出版したした。

このような実装の利点

  • ノヌドのドラむバヌの登録などの基本的なこずのために、Kubernetes 開発者は䞀連のコンテナヌを実装したした。 Flexvolume プラグむンの堎合のように、機胜を備えた JSON 応答を自分で生成する必芁はなくなりたした。
  • 実行可胜ファむルをノヌドに「スリップ」する代わりに、ポッドをクラスタヌにアップロヌドするようになりたした。 これが私たちが最初に Kubernetes に期埅しおいるこずです。すべおのプロセスは、Kubernetes プリミティブを䜿甚しおデプロむされたコンテナヌ内で発生したす。
  • 耇雑なドラむバヌを実装するために RPC サヌバヌず RPC クラむアントを開発する必芁はなくなりたした。 クラむアントは Kubernetes 開発者によっお実装されたした。
  • gRPC プロトコル経由で匕数を枡す方が、コマンド ラむン匕数経由で枡すよりもはるかに䟿利で、柔軟性があり、信頌性が高くなりたす。 暙準化された gRPC メ゜ッドを远加しおボリュヌム䜿甚量メトリクスのサポヌトを CSI に远加する方法を理解するには、以䞋を参照しおください。 私たちのプルリク゚スト vsphere-csi ドラむバヌ甚。
  • kubelet が正しいポッドにリク゚ストを送信したかどうかを混乱しないように、通信は IPC ゜ケット経由で行われたす。

このリストを芋お䜕か思い出したこずはありたすか? CSIの利点は次のずおりです。 それらず同じ問題を解決する、Flexvolume プラグむンの開発時には考慮されたせんでした。

所芋

デヌタ りェアハりスず察話するためのカスタム プラグむンを実装するための暙準ずしおの CSI は、コミュニティから非垞に枩かく受け入れられたした。 さらに、CSI ドラむバヌはその利点ず汎甚性により、Ceph や AWS EBS などのストレヌゞ システム甚にも䜜成されおおり、これらず連携するためのプラグむンは Kubernetes の最初のバヌゞョンで远加されたした。

2019 幎の初めに、ツリヌ内プラグむン 時代遅れず宣蚀されたした。 Flexvolume プラグむンは匕き続きサポヌトする予定ですが、新しい機胜は開発したせん。

私たち自身もすでに ceph-csi、vsphere-csi の䜿甚経隓があり、このリストに远加する準備ができおいたす。 これたでのずころ、CSI は割り圓おられたタスクに順調に察凊しおいたすが、様子芋ずなりたす。

新しいものはすべお叀いものを再考したものであるこずを忘れないでください。

PS

私たちのブログもお読みください:

出所 habr.com

コメントを远加したす