TL;DR
- KubernetesでRaw Block(Raw Deviceともいう) VolumeがBeta版になった。
- Raw Block(Device)とは何なのか。メリットは?
- Kubernetesから見たRaw Block対応の意味
KubernetesのRaw Block VolumeサポートがBetaに
去る3/8、KubernetesのRaw Block Volume サポートがBetaとなったことが発表されました。
#Kubernetes v1.13 moves raw block volume support to beta, allowing persistent volumes to be exposed inside containers as a block device instead of as a mounted file system. More on the blog ⬇️⬇️https://t.co/B8RsRWZWS1
— Kubernetes (@kubernetesio) 2019年3月8日
私(@tzkb)は「Kubernetesでデータベースを動かそう」なる活動をしていますので、今回の一報に歓喜したのですが、DBでもRawデバイスの利用は減ってきています。そこで歴史的な背景を振り返り、今KubernetesがRaw Block Volumeをサポートする意味を再考したいと思います。
歴史から振り返るRaw Block(Device)の意義
今回のKubernes公式のアナウンスをまとめると、以下が書かれています。
- Raw Block Volumeはファイルシステムのオーバヘッドを回避する選択肢であること
- ユースケースとしてデータベースとSDS(Software Defined Storage)を想定していること
まず、1.についてオーバーヘッドとは何のことなのかを見ていきましょう。
ファイルシステムのオーバーヘッドとは何か?
Why add raw block volumes to kubernetes? の冒頭には以下のように書かれています。
There are some specialized applications that require direct access to a block device because, for example, the file system layer introduces unneeded overhead.
たとえば、ファイルシステム層に不要なオーバーヘッドが発生するため、ブロックデバイスに直接アクセスする必要がある特殊なアプリケーションがいくつかあります。
ファイルシステムの利用で発生するオーバーヘッドといわれて私が思いつくのは、
- ジャーナリングファイルシステムによるもの
- カーネルキャッシュによるもの
の2つです。
ジャーナリングファイルシステムのオーバーヘッド
私がデータベースをさわり始めた約20年前には商用UNIXにデータベースを乗せることが一般的で、Oracle(当時はOracle8の頃)利用時には、UNIXが持つジャーナリングファイルシステムを経由せずに、RAWデバイスにデータファイルを置くという構成がベストプラクティスでした。
その理由として以下があげられていたと記憶しています。
- そもそもDBレイヤでログ先行書込みがされており、ファイルシステムでジャーナルを書く必要はない
- ジャーナルログの書き出しでIOパフォーマンスが落ちる
当時のOracleはRAWデバイスを扱うことが出来たので、主に性能上の観点からRAWデバイスを選ぶというのは妥当な選択肢でした。
しかし、RAWデバイスの扱いは非常に煩雑です。そのため、利便性を下げてまでRDBMSでRAWデバイスを使う理由は今はない、というのが個人的な見解です。Oracle12c以降、RAWデバイスは非サポートになっていますし、他のOSSデータベースでも、私の知る限りサポートしているものはありません。
※ちなみにジャーナリングファイルシステムって何?という方はこちらなども参考にどうぞ。
カーネルキャッシュのオーバーヘッド
もう一つのカーネルキャッシュについては、2010年頃にPostgreSQLのIOを説明するために記述した図を載せておきます。
この図で言いたかったのは、ファイルシステム経由のIOはカーネルキャッシュ(図中ではページキャッシュ)を使う、ということです。データベースではこれが冗長になります。つまり、DBサーバにおいて重要な物理メモリが、データバッファ以外にカーネルキャッシュとしても使われてしまうのです。それらにバッファリングされるデータが同じものになってしまうことも良く見られます。
しかし、このメモリ部分の冗長性も、昨今のLinuxではDirectIOの対応により回避できるようにとなっています。MySQLではinnodb_flush_methodによりDirectIOを指定することができます。PostgreSQLでは現時点でこれに対応するパラメータはありません。
※ここまでのRAW、DirectIOの関係をまとめた記事はこちらが分かりやすいです。
KubernetesにおけるRaw Block Volumeの利用シーン
歴史的な話が長くなりました。
ここまで見てくると、データベースでRAWデバイスが必要とされてきた大きな問題は解消されており、OracleやMySQL、PostgreSQLが対応を打ち出していない点からDBレイヤでは今後もサポートする必要がない、というのが一般認識になりつつあるように見えます。
では、KubernetesにおけるRaw Block Volumeの利用シーンを上の2点以外で考えてみましょう。
Open-Channel SSDの紹介
2019年のSNIA-jのトレンドセミナーでも紹介されたOpen-Channel SSDというものがあります。
※この辺りを見るとプロジェクト概要が載っています。
これはSSD側のコントローラでやっていた処理をSW化して、ホスト側に持っていこうというプロジェクトです。そうすることで、
- IOの並列度をアプリケーション側で細かく管理できる
- SSDのライトアンプリフィケーションをアプリケーション側で管理することで、IOの安定化が可能
- SSDのコストが低くなる(コントローラがpoorで良い)
というメリットがあります。
RocksDBのOpen-Channel SSD対応
では、このOpen-Channel SSDをデータベースで利用している例を紹介しましょう。残念ながらRDBMSでの事例は見つかりませんでしたが、いわゆるNoSQLと呼ばれるRocksDBというものが見つかりました。
資料はこちらにありますが、非常に細かくIOをアプリケーション(ここではRocksDB)から制御している様子が見てとれます。
上記のRocksDBで見られるように、データベースのIO最適化をハードウェアに近いレイヤで行うというの考え方は、OracleのExadataやAmazonのAuroraでも見られます。
さらにMySQLではストレージエンジンがPlaggableであり、PostgreSQLでもPlaggable Storageへの対応が議論されています。そのことから、RocksDBのOpen-Channel SSD対応のような形がストレージエンジンの一つの形として今後登場してくる可能性があります。
KubernetesレイヤでのIO最適化が可能になる(かもしれない)
RocksDBでのOpen-channel SSDのように、最新デバイスのIO性能を最大限に引き出すためにファイルシステムではなくRaw Blockとして扱うケースが今後出てくるでしょう。
そして、それらの実装を**"そのまま"**Kubernetes上で動かすというワークロードで、今回のRaw Block Volumeサポートが活躍してくれるのではないか、というのが現時点での私の見解です。
今、巷ではNVMe-SSDや不揮発性メモリと呼ばれるようなIOデバイスの進化が著しいですが、それらを活かすために、DBMSだけでなくCloud Native Storageでもハードウェア層まで踏み込んだ実装の形が見られるようになる、と私は考えています。
まとめ
「Kubernetesはクラウド時代のOSになる」と言われたのは2017年だったと思いますが、今回のRaw Block VolumeサポートはこのOSとしての可能性を拡げる機能になるでしょう。
今回は書くことができませんでしたが、CSIの状況も合わせてウォッチしながら、Rawデバイスとしてのボリューム利用について今後も情報を集めていきたいと思います。