Kubernetes is 何
先週末、Docker、IBM、Microsoft、RedHatがGoogleのコンテナ管理フレームワークKubernetesに開発参加を表明して話題になったが、この連携がどんな意味を持つのかすぐにピンときた方はどの程度いるだろうか。その前に、Kubernetesって何? Dockerとどう関係するの? 読み方すら分からないんだけど……って反応が多いと思う。
Googleのソフトウェアエンジニアで、Kubernetesの開発者であるBrendan BurnsによるGoogle I/O 2014のセッションContainerizing the Cloud with Docker on Google Cloud Platformを見ると、彼は「クゥバネィテス」と呼んでいる。
From Containerizing the Cloud with Docker on Google Cloud Platform
Kubernetesのロゴはこんな感じ:
そして6月のDockerConに合わせてGoogleがGitHub上でベータ版を公開したKubernetesのDesign Overviewの概要には、以下のように記されている。
Kubernetes builds on top of Docker to construct a clustered container scheduling service. Kubernetes enables users to ask a cluster to run a set of containers.
「Kubernetesは、Dockerコンテナによるクラスタ構築のためのスケジューリングサービス」である。要するに、Dockerがこれから本格的に普及し、何も考えずにバンバン大量にコンテナのクラスタを作り始めると、各VMへのコンテナの割り振りや管理がやっかいな問題となる。それを取りまとめようとのもくろみで開発されているジョブスケジューラである。
Kubernetesに含まれるサンプルコードは今のところGoogle Compute Engine (GCE)でのみ動作するが、Kubernetes自体はGCEに依存していない独立したオープンソースツールであり、今後は参加ベンダー各社のクラウドへの対応が進むと思われる。
この生まれて間もない、運用実績もほとんどないオープンソースの単なるジョブスケジューラーに対して、なぜ錚々たるクラウドベンダー各社がこぞって協力を表明しているのか。それを理解するには、Dockerとコンテナ技術がなぜこのタイミングでクラウド業界でここまで大きくクローズアップされているか、背景を知らないと分かりにくい。
そもそもDocker is 何
Dockerの意義については、yuguiさんの記事Dockerで何が変わるのかが分かりやすい。要点を抜き出すと、
Dockerとはいわゆるコンテナ技術の1つで、Linuxホスト環境の中に隔離された別のLinux環境を作ってくれる技術だ。 軽量仮想マシンと呼ばれたりもする。
仮想マシンに似ているという観点から述べるなら、コンテナ技術というのはマシンやOSそのものを仮想的に実現してその上でアプリケーションを動かす代わりにマシンとカーネルはホストのものをそのまま使って、ユーザーランド+αだけを仮想化する、みたいなもんだ。別の視点から述べると、これって要するにchroot+αだ。「ちょっとすごいJail」と言ってもいいだろう。
Dockerが新しいのは、コンテナ環境で走らせるアプリケーションを簡単にパッケージする標準的な方法を確立したことにある。(中略)こうして作成された差分ディスクイメージを走らせるときもホスト環境のディスクを無駄に使わず、起動時にマージなんてアホなことをすることもなく、効率的にインスタンス化できるようになっている。こういう便利なパッケージの仕組みをオープンソースで作った。そしてこの仕組みをみんなが使い始めた。
From Docker Meetup Tokyo
yuguiさんが指摘するように、Dockerには2つのメリットがある。
- コンテナ技術
- 差分ディスクイメージのソーシャルなシェア
これらのうち、後者についてはDockerを触ったことにある方ならすぐに理解できるだろう。Dockerが普及した最大の要因、そしてDockerが新しかった点は、差分イメージのシェアやキャッシュによるビルド作業の簡単さである。まっさらな状態からアプリケーションスタックを構築する作業をごく短い時間で行え、環境構築のスクラップ&ビルドがとても容易になる。
しかし、大手各社が突如としてDocker界隈に参入し始めた要因は、それだけではない。このDockerのビルドの便利さを通じて、「コンテナ技術に対する世間のリテラシーがぐんと高まったこと」が、ブレークスルーなのである。みんながDockerに触り始めたことで、そのコンテナの便利さが着実に理解されつつある。あれ、なんでこれあっという間にまっさらなOS環境を用意できるの? VM起動を待たなくてもよいの? VMとは何だったのか?
商用UNIXにコンテナ技術の最終形態を見る
VMを用いずにコンテナやパーティションにより独立したOS環境を提供する仮想化技術は、Linux以前の商用UNIXの時代から(さらにはメインフレームの時代から)実用化されていた。しかし、Linux後の世界ではDockerが現れるまでここまで広く一般に認知されることはなかった。
Dockerのコンテナ技術は、yuguiさんの記事のように「要するにchroot、Jail」と表現されることも多い。しかし、コンテナ技術の最終形態は単なるchrootにとどまらない。Dockerを介して提供されているコンテナ機能は、SolarisやHP-UX等の商用UNIXが90〜00年代に実用化してミッションクリティカル環境でばりばり運用していたコンテナ技術の域には全然達していないのだ。
ひとつはセキュリティ。Dockerのコンテナはセキュリティが甘いとしばしば指摘されるが、そもそも商用UNIXにおけるコンテナもしくはパーティションとは、単一OS内部での厳格なセキュリティ隔離のために生まれたものだ。例えばHP-UX Containersは以前はSecure Resource Partitionと呼ばれ、その源流は米国防総省が求めたセキュリティ規格TCSEC B1レベル準拠のセキュリティ隔離を実現する技術Virtual Vaultにたどり着く。異なるコンテナ間は別々のマシンで動作しているのと同等の隔離性が得られるほか、ロールベースのアクセス制御によるコンテナ間リソース共有が提供されていた。
From Making the Adaptive Enterprise Vision a Reality: The HP Partitioning Continuum
もうひとつは、CPUやメモリ、I/O等のサーバーリソースの隔離性。Dockerでは、どれか一つのコンテナが暴走したりすると他のコンテナに大きく影響したという話も聞く。一方で、HP-UX Containersでは、標準のHP-UXでは利用できない有償オプションのカーネルスケジューラーFair Share Scheduler (FSS)を使い、各コンテナに割り当てられるCPU時間が厳格にコントロールされる。となりのコンテナでプロセスが暴走してもビクともしない。Solarisのコンテナ技術Solaris Containerにも同様のFSSが利用されていた。
From 「サーバ仮想化によるスケールアウト」の新潮流・後編
HP-UXやSolarisのコンテナでは、このFSSの設定を動的に変化させることで、各コンテナに配分するCPUやメモリ、I/Oリソースをコンテナの負荷状況に応じて最適に配分できる。そのモニタリングとオーケストレーションを司るワークロードマネージャも提供されていた。
このように商用UNIXの世界では、コンテナ技術によるセキュリティやサーバーリソースの厳格な隔離をはじめ、多数のコンテナ間の動的なリソース配分最適化やオーケストレーションまでが90〜00年代には実用化されており、IT社会の根幹を支える基幹系に投入されていた。今からするとなんだかオーパーツのようなロストテクノロジーなのである(基幹系にがっちり入っている技術は事例等をおおっぴらに喧伝できないため、オープンソース分野に伝承されず途絶えている優れた技術も少なくない)。
アプリの入れ物としてのVM
話を現代に戻すと、これまでVMは何のために使われていただろうか? 一義的には「1台の物理サーバー上で複数のアプリケーションを安全に運用するための論理的な入れ物」を用意するためである。しかしもし、商用UNIXのようにセキュリティやサーバーリソースをきっちり隔離してくれるコンテナを1秒で作れる環境が最初からあったなら、はたしてVMは今ほど多数作られていただろうか? 個々のVMのゲストOSイメージを個別管理したり、セキュリティパッチを慌てて当てたり、OS起動に数分待ったり、ホストOSとゲストOS間のダブルバッファリングによるI/O性能低下に悩んだり……といった様々なオーバーヘッドを考えると、しっかりしたコンテナがあればアプリの入れ物はそれで十分ではないか、という発想が当然生まれてくる。
Googleはすべてのサービスをコンテナで運用
それを10年前から実践してるのがGoogleで、今年5月のGlueConでのセッションContainers at ScaleにおいてソフトウェアエンジニアJoe Bedaがカミングアウトした。
「Googleではすべてのサービスをコンテナで運用している。週に20億個のコンテナを起動している」
From Containers at Scale
上図は、同セッションでJoeが解説したGoogle社内のコンテナ管理フレームワークの概要である。ベアメタルサーバー上にホストOSが稼働し、クラスタスケジューラによって個々のサーバーにコンテナがデプロイされる仕組み。この図にはVMは存在しない。つまり、Google検索からGmail、Map、Docs、そしてGCPもなにもかも、すべてベアメタルサーバー上のコンテナで直接稼働しているのだ。この事実を知っていた、そーんなーのー常識〜♪という方はいったいどの程度いるのだろう? 私にとっては、GoogleがGlueConでこう言い切ったという事実は、クラウドの時代の転換点と言えるくらい感慨深いものであった。
いつからクラウド=VMと錯覚していた?
しかもこれはGoogleに限った話ではない。Facebookもクラウド構築には仮想化は使っていないと公言している。
"We find within our testing that a realised (non-virtualised) environment brings efficiencies and the ability to scale much more effectively," Coglitore said. "When we look at the operational realities, we very much would like to lose a server and not have it impact our experience, but as your start to virtualise the importance of that server becomes enhanced and at scale becomes difficult."
From Facebook: Virtualisation does not scale
- 我々のテスト環境では仮想化を使わない環境の方が効率性に優れ、スケーラビリティの格段に高かった
- 仮想化を使うとサーバ障害の影響が大きくなりスケールしにくくなる
GoogleやFacebookといったいわゆる“クラウド”の最大手たちがこぞって仮想化を主要なサービス運用に使っていないとすれば、もしかするとVMによる運用はクラウドではマイノリティなのではないのだろうか? 商用UNIXに匹敵する高いコンテナ技術を持たないクラウド事業者のための過渡的な技術なのか? といった見方さえ生まれてくる(ただもちろん、GoogleはコンテナにはないVMの様々なメリットを否定しているわけではないし、私もそうだ)。
Kubernetesが描く世界
ここまで読めば、クラウドベンダー各社が突如としてDockerに参入しだしたりKubernetesに開発参加したりする動機が分かるだろう。つまり世の中の多くのエンジニアがDockerを通じてコンテナの味を知り、オープンソースやクラウドの世界がVMからコンテナへと大きく舵を切りつつあることを、各社は敏感に感じ取っているのである(←個人の感想です)。それは、いちスタートアップが始めた単発的な思いつきのアイディアではなく、商用UNIXベンダーでの基幹系での実績に始まり、GoogleやFacebookが10年も前から世界最大規模の複数のクラウドで導入して商業的成功を収め、いまも拡大を続けている手法だ。
ラベルを使いコンテナの集まりを抽象化
しかし現在のDockerにはいろいろ足りないものがある。過去10年の経験で得たベストプラクティスや知見をもとに、その足りない部分をオープンソースソフトウェアとして実装、公開し、補っていこうとしているのが、GoogleのKubernetesである。
足りない点の一つが、大規模クラスタにおけるジョブスケジューリングの問題。例えば複数のコンテナホスト上に何も準備なしでたくさんのコンテナをデプロイし始めると、当然ながらその運用はカオスになってしまう。そこでKubernetesではまずlabel
に基づくコンテナの分類を導入する。このlabel
の種類は自由に定義でき、例えばrole
としてfrontend
とbackend
、stage
としてproduction``stage``dev
と分類する、といった具合。
From Containerizing the Cloud with Docker on Google Cloud Platform
そしてデプロイする際には、Replica Controller
に対してlabel
とコンテナ数を指定する。すると、同コントローラーが現在利用可能なホスト群に対してデプロイする。コンテナは死活監視されるためいずれかのコンテナが落ちると指定のコンテナ数を満たすように新たに補充されるほか、コンテナ数の動的な変更や、イメージのローリングアップデート、ロールバックも可能。
From Containerizing the Cloud with Docker on Google Cloud Platform
また同時に、複数のコンテナで構成されるService
を定義し、その稼働ポート番号を指定する。例えばNginxやRedis、MySQLといった各サービスが稼働する複数のコンテナをグループ化し、手前にロードバランサーを据える。サービスを使う側は特定のIPやポートを使うだけでよく、個々のコンテナの存在を意識させない仕組みになるという。
From Containerizing the Cloud with Docker on Google Cloud Platform
このI/OセッションでBrendanが強調していた点は、こうしたレプリカやサービスという単位で抽象化することで、個々のコンテナやサーバーを意識させないインフラ構築が可能になるということだ。
Kubernetesの今後を知るにはLMCTFY、GAE、Omegaを見よ
もっとも、現時点のKubernetesができることはあまり多くない。Googleが社内で用いているコンテナ管理フレームワークそのものではないし、開発も始まったばかりであるため、機能的にも実績的にもスタートラインに立ったところ。Googleは今後、同社内で過去10年の間に培われてきたコンテナ技術のノウハウをKubernetesに投入していくとしている。
今後のKubernetesに盛り込まれていくであろう技術を予測する上では、Googleがすでに公開済みのコンテナ技術が参考になる。そのひとつ、2013年に公開されたLMCTFY (Let Me Contain That For You)に関する発表スライドでは、LMCTFYが提供するジョブスケジューリングの最適化手法が紹介されている。個々のコンテナが必要とするCPUやメモリ、I/Oリソースに対し、コンテナホスト側で提供可能なリソース状況を照らして最適な配分を行うというものだ。例えば、CPUヘビーなコンテナ、I/Oヘビーなコンテナ等がそれぞれ特定のホストに集中しないよう分散させる、といった具合。
From LPC2013 Let Me Contain That For You
そしてGoogleが公開しているコンテナ技術のもっとも分かりやすい例は、Google App Engine (GAE)である。GAEにデプロイしたアプリケーションは「アプリケーションインスタンス」と呼ばれる単位でスケールアウトしていくが、このアプリケーションインスタンスはセキュリティ、CPU、およびメモリリソースがきっちり隔離され、ポータビリティが確保されたコンテナに他ならない。
From Unleashing App Engine Scalability
だからこそ、HTTPリクエストの到着後50msでインスタンスを起動できたり、全世界のSnapChatユーザーのトラフィックスパイクをさばくために一瞬にして大量のインスタンスをスケールアウトさせたりといった、VMでは実現の難しい鬼のようなスケーラビリティを運用いらずで実現できているわけである。Kubernetesもいずれはこの世界をオープンソースで実現することを狙っているはずだ。
またGoogleが社内で用いている大規模ジョブスケジューラはOmegaと呼ばれ、ペーパーが公開されている。このペーパーでは、サーバーリソースに対してコンテナをデプロイする際に、リソースの確保を保守的並行制御で行う代わりに楽観的並行制御を用いた方が大規模環境ではスケールしやすい、といったノウハウが説明されている(もうちょっと詳しく触れようかと思ったけど、ここまで書いて力尽きた)。
Kubernetesはコンテナ時代のクラウド標準になり得るか?
以上、ここではKubernetesが生まれた背景と現状、今後の姿について考えた。今の段階ではベーダ版でありまだまだ実運用に投入するには尚早であるが、ベンダー各社の協力によって現在のクラウドをひっくり返せるだけのモメンタムを得られるのかが興味深いところだ。
Disclaimer この記事は個人的なものです。ここで述べられていることは私の個人的な意見に基づくものであり、私の雇用者には関係はありません。