Cloud Penguins

Flying penguins in the cloud.

コロケ芸の実例を見せながらBOSHのops fileの書き方を解説する

Cloud Foundry Advent Calendarの19日目

前回の投稿でCFにはコロケ芸というリソース節約方法があるということを書いたのですが、記事を公開した直後に同僚making氏から速攻でツッコミが。

すみませんすみませんすみません。

前回記事を書いたとき、手元でも動作する例を用意していたのですが、それはmanifestを直接修正してデプロイする形にしていました。 BOSH v1であればこうするしかなかったんですが、もう時代はBOSH v2。BOSH v2であればmanifestを直接修正するのは古い。やはりここはops fileを使わねば。

ということで、CFをコロケする例を示しつつ、併せてops fileをどう書いていくかという話をしたいと思います。

そもそもOps fileとは

正確にはOperations fileっていいます。

https://bosh.io/docs/cli-ops-files.html

ベースとなるYAMLに対して、特定の記法でops fileを渡すことで、値のオーバーライドや削除を行うことができます。

たとえば以下のようなベースYAMLがあったとして

name: my-cf

以下のようなOps fileを加えると

- type: replace
  path: /name
  value: other-cf

以下のような出力が得られます

name: other-cf

Path

ベースとなるYAMLのどの部分を指定するかを、このpathで表現します。

/と指定するとYAMLのルートを示します。上記の書き換え例だと、ルートに連なるnameというkeyに対して操作を行いたいので、/nameと指定しています。

他にもシンタックスがあるため、ドキュメントをを参照してください。

https://bosh.io/docs/cli-ops-files.html

Operation

上記のops file例でいうと、typeの部分がoperationに当たります。ここにはreplaceもしくはremoveを指定することができます。

pathに対して、値をreplaceするのか、あるいはremoveするか。replaceする場合は、valueで指定した値に差し替わります。

Ops fileで何が嬉しいの

CFをデプロイする場合、今後はcf-deployment を使ってデプロイするのが主流になりますが、たとえばこのデプロイするCFにカスタマイズをしたいとします。

昔のBOSHですと、この中のcf-deployment.ymlを直接編集するしかありませんでした。 しかし、このやり方はcf-deploymentをフォークしてしまうことになり、upstreamが更新された際にコンフリクトを起こしてしまうことになります。これはスマートなやり方とはいえません。

そこで、カスタマイズしたい内容をops fileとして切り出すことで、ベースとなるcf-deploymentに手を加えること無く行うことができます。

cf-deploymentのリポジトリには、よくあるカスタマイズについてはあらかじめops fileが同梱されており、-o オプションで指定するだけで適用することが可能です。

cf-deployment/operations at master · cloudfoundry/cf-deployment · GitHub

コロケするOps fileを作ってみよう

ということで、今回は例としてCloud ControllerとUAAを同居させる「Control」VMを作成する例を作ってみました。 完成版Ops fileはこちらにおいてあります。

UAAとAPIの中身をマージする

以下が、単純にUAAとAPIのjobをマージしたyamlです。

https://gist.github.com/jacopen/e447fb3f409ae5935c9e69c27dcae531#file-first-yml

これで流せば無事コロケ完了・・・かというとそうはいきません。いくつか問題点があります

  • 項目かぶり -- この例でいうとstatsd_injectorやroute_registrarなどの項目が重複しています。このままではエラーになってしまうため、この中身も適切にマージしてあげる必要があります。
  • ポートかぶり -- このJobsでは明示されていませんが、実はUAAとpolicy-serverはともにデフォルトで8080で上がってしまいます。このままではポートかぶりにより、どちらかのプロセスが正常に立ち上がりません。どちらかの設定を被らないポートに変更してやる必要があります。

ということで、ここのあたりは地味ーな作業をやって良い感じにコロケできる設定を作っていきます。

既存のUAAとAPIを無効にする

ControlVMでUAAとAPIをデプロイしてしまうので、以下のようにremoveを書くことで個別のVMが作成されないようにしました。

- type: remove
  path: /instance_groups/name=uaa
- type: remove
  path: /instance_groups/name=api

1az構成にする

Multi AZにするのであればこの作業はスキップできますが、今回はコロケで極限までVMを削る、というのを試してみたいので、1AZ構成に変更したいと思います。

cf-deploymentの中の operations/scale-one-az.yml を指定すると、1AZ構成に変更されます・・・が、今回はuaa/apiをremoveしてしまったため、単純に食わせるとエラーになってしまいます。ということで、美しくないですがopsfileの中に該当ファイルからuaa/apiを抜いた項目を追加する形にしました。(もっと良い案思いついたらなんとかします)

同じ理由で、NW名を引数で渡せるようにする operations/rename-network.ymlの中身も含めてしまっています。

ということで完成版

Collocate UAA and API · GitHub

・・・なんかもっとシンプルかつスマートにずばっとコロケできるようなのを目指したんですが、何か・・・長いですね。 とはいえcf-deployment.ymlを直接弄ってしまうよりはマシなものになっている、たぶんきっと。

あとは-oオプションでこのops fileを指定してやれば、デプロイできるはずです

bosh deploy -d cf cf-deployment.yml --vars-store env-repo/deployment-vars.yml -v system_domain=example.com -v network_name=bosh-network -o collocate.yml

必要にに応じて他のops fileも読ませてデプロイしてください。ただ、/instance_groups/name=apiや/instance_groups/name=uaa を操作するops fileの場合、エラーがでちゃうかも。

おいでよコロケ芸の森

Cloud Foundry Advent Calendar 2017の13日目

最近どうぶつを高く積み上げていくe-sportsを始めてみたのですが、あれよあれよと時間を吸われます。やばい。

さてみなさん。コロケ芸という言葉をご存じでしょうか。

もし知っているという人は、おそらく某所関係者かと思われますので多分この記事読まなくても大丈夫です。

CFの必要リソースでかいねん問題

Cloud Foundryの構築はBOSHを用いますが、BOSHはVMを用いてデプロイを行う仕組みなので、コンポーネントが増えれば増えるほどVMの数がすごいことになります。Cloud Foundryは数多くのコンポーネントから成りますので、デプロイするだけでものすごいVM数になります・・・というのは、CFに関わる人であればご存じでしょう。

きちんと理由があってコンポーネントが分けられているので、BOSHで管理する以上VM数が増えてしまうのは仕方ない・・・と言いたいところですが、とはいってもやっぱりコンパクトな環境でフル機能CFを使いたい。 BOSH-lite でAll in oneを構築してしまう手はありますが、そうではなく・・・と。

「なんとかしてリソースを節約しつつもプロダクションレディなCFクラスタを構築したい」

そういう考えから、VMに多くのコンポーネントを同居させつつも運用性は失わない、コロケーションのノウハウ、すなわちコロケ芸が、都内某所で脈々と受け継がれているという噂があります。

コロケ芸の広まり?

そんな門外不出のコロケ芸ですが、やはり同じことを考える人は多いようで。

Pivotal Cloud Foundryを提供するPivotalが、9月にリリースしたバージョン1.12で"Small Footprint Runtime (SRTと略す)"というリソース削減版を公開しました。これはまさに、コロケ芸そのものだったりします。

SRTの仕組み

Pivotalのドキュメントを見ると、以下のようなことが書いてあります。

The Small Footprint Runtime is a repackaging of the Elastic Runtime components into a smaller and more efficient deployment. A standard Elastic Runtime deployment must have at least 24 virtual machines (VMs), but the Small Footprint Runtime requires only 14.

24必要だったVMが14になる!とのこと。・・・うーん、確かに大きく減りましたがびっくりするほどの削減ではないですね・・・。 ですが、よく見てみましょう。

f:id:jaco-m:20171213195124p:plain

よく見ると、必要と言われているVMのうち多くをErrandが占めていることがわかります。ErrandはBOSHでrun-errandを行ったときに必要になってくるVMであり、常に立ち上がっているVMではありません。そのため、本当の意味で必要なVMはより限られることになります。

この図の中で、CF自体の動作に必要なVMは以下の4つのみです。

  • Control
  • Compute
  • Router
  • Database

つまり、HAを考えないのならば4VMでいける、というわけです。

コロケの実現方法

さてこのコロケ芸、どうやって実現しているんでしょうか。Pivotal Cloud Foundryも内部的にはBOSHなので、OSS CF でも同じことは出来るはずです。

cf-deploymentのUAAの記述をみてみましょう

https://github.com/cloudfoundry/cf-deployment/blob/master/cf-deployment.yml#L367-L577

インスタンス数、VMの種類の指定が続いたあと、jobs: にてどのjobをどういう設定で構築するか記述されていることが分かるでしょう。 もしUAAとCloud Controllerを同居させたい場合は、両方のJobを動かせるだけのインスタンスを指定し、jobs: の項目をマージしてやればいけそうです。

・・・というと簡単そうに聞こえますが、実際にはなかなかムズかしかったりします。そもそもマージさせていく作業が超絶地味だったり、jobの中でも重複する項目があったりと。

もしVM数を削減してみたいという方は、是非一度チャレンジしてみてはどうでしょうか

PCFを買ってSRTでセットアップすれば一瞬ですが

どういう単位でコロケするか

どのJobをどうコロケーションさせていくのがいいか。これは知恵の出しどころかなと思います。 たとえばコロケさせたうち特定のJobだけ過負荷でスケールアウトさせないと・・・という場合、コロケの仕方によっては不要なJobまで増やしてしまい、リソース削減のために行ったコロケが逆効果なんてことも起きえます。

先ほども紹介した、PCFのSRTはその分け方の参考になるかもしれません。

  • Control
  • Compute
  • Router
  • Database

の4VMが必須と書きましたが、そのうちComputeはdiego-cellそのものです。他のものは同居していません。 また、Routerに関してもGorouterそのものです。

つまり、CFを使う上で一番負荷がかかりやすいであろう、Gorouterとcellだけは他と同居させず、そのままというわけです。

CFの主要なコンポーネントの多くは、Controlに集約されています

f:id:jaco-m:20171213212033p:plain

また、Consul, NATS, MySQLに関してはDatabaseに集約されます

f:id:jaco-m:20171213212122p:plain

Consulは仕組み上、クラスタを組むのであれば3台, 5台といった奇数にする必要があります。つまり、HAで組む場合Databaseは3台必要ということになりますね。

ControlやRouter, Computeは2台以上あればHA構成になります

ここらでひとつCFの昔話をしながら変遷を振り返る(その2)

Cloud Foundry Advent Calendar 2017の11日目

前回に引き続きCFの昔話を。

言語

現在のCFはほとんどがGoで書かれていますが、CFv1はRubyで書かれていました。CFv2も当初はRubyで書かれていましたが、徐々にGoに書き換えられていきました。

現在Rubyが残っているのはCloud Controllerくらいでしょうか。なおUAAに関しては出た当初から今に至るまでJavaで書かれています。おそらくSpring Securityを使いたかったからかと思われます。

Router

現在はGoで書かれたGorouterが使われていますが、CFv1からCFv2の初期に使われていたRouterは、Nginx+Lua+Rubyという構成でした。

github.com

NATS経由でのルーティング情報のやりとりはRubyで書かかれたアプリケーションが担い、実際にトラフィックを捌くのはNginx+Luaという仕組みです。 枯れているNginxを利用しているだけあってパフォーマンスは悪くなく、Gorouterの登場当初は旧Routerよりも速いというのが公式の見解でしたが、実際には旧Routerのほうがパフォーマンスが良いというケースもしばしばありました。

CLI

CFv1はcfコマンドではなく、vmcコマンドというものを使っていました。

vmcコマンドはRubyで書かれており、利用するにはまずRuby環境をととのえ、その上でgem install vmcを行う必要がありました。今みたいにGolangで書いて1バイナリで配布なんてことが出来なかった時代です。

現在でもRubygems.orgに残っており、インストールできます。(といっても使い道はないですが)

vmc | RubyGems.org | your community gem host

最終バージョンは0.5.1となっていますが、0.5系や0.4系は非常に不安定であり、かつUAA導入の過渡期でもあったため、利用できない環境が数多く存在しました。

CFv1利用者の中では「CFを使うならvmc 0.3.23を使え」が合い言葉であり、結局CFv1終焉まで0.3.23が利用され続けました。

vmc tunnel

vmcコマンドでユニークなものとしては、vmc tunnel コマンドが挙げられます。 vmc tunnelコマンドを打つとCF上にcaldecottと呼ばれるアプリがデプロイされ、caldecottとvmcコマンド間でトンネルが張られ、サービス(MySQLやPostgres)にコマンドを打ったりdumpしたり出来ました。

なぜか当時は存在しなかったはずのPivotalのサイトにblog記事が残っていました。 Now You Can Tunnel into Any Cloud Foundry Data Service

$ vmc tunnel postgresql-12345

Trying to deploy Application: 'caldecott'.
    Create a password: 

Uploading Application:
 Checking for available resources: OK
 Processing resources: OK
 Packing application: OK
 Uploading (1K): OK
Push Status: OK
Binding Service [postgresql-12345]: OK
Staging Application: OK
Starting Application: OK
Getting tunnel connection info: .OK

Service connection info:
 username : ua76003139485469989d57b22f9cb83xx
 password : p8214ebd2a7254698913e01c86a4432xx
 name : da281fa2162f947028876d0500ae31cxx

Starting tunnel to postgresql-12345 on port 10000.
1: none
2: psql
What client would you like to start?: 2
Launching 'PGPASSWORD='p8214ebd2a7254698913e01c86a4432xx' psql -h localhost -p 10001 -d da281fa2162f947028876d0500ae31cxx -U ua76003139485469989d57b22f9cb83xx -w'

psql (9.0.4)
Type "help" for help.
da281fa2162f947028876d0500ae31cxx=> d
                     List of relations
 Schema | Name  | Type  |               Owner
--------+-------+-------+-----------------------------------
 public | hotel | table | ua76003139485469989d57b22f9cb83xx

da281fa2162f947028876d0500ae31cxx> select * from hotel;
  1 | 3555 S. Ocean Drive                    | Hollywood           | USA           | Westin Diplomat                | 199.00 | FL        | 33019
  2 | 890 Palm Bay Rd NE                     | Palm Bay            | USA           | Jameson Inn                    |  60.00 | FL        | 32905
  3 | The Cottage, Southampton Business Park | Southampton         | UK            | Chilworth Manor                | 199.00 | Hants     | SO16 7JF

結構便利じゃないですか?これ。

vmcコマンドからサービスに直接psqlコマンド叩きにいけるんですよ。

CFv2に移行して一番不便に感じたのが、この機能が無いことでした。初期のCFv2はcf sshコマンドも無かったため、v1で出来たこのあたりの操作を行う代替案が限られていたんですよね。

CFv1のデプロイ方法からBOSHに至るまで

現在はCFといえばBOSH、BOSHといえばCFというくらい重要な存在になっていますが、BOSHはCFv1の開発と運用の結果、既存の仕組みでは運用に耐えられないということで開発されたものです。つまり、CFv1はBOSHじゃない別の仕組みを使っていたというわけです。

CFv1は、dev_setupというchef-soloを利用した仕組みでデプロイを行っていました。

github.com

chef-soloですのでそのままでは複数台構成にできません。そこで、CFを構築する人たちはcapistranoなどを使ってdev_setupを各ノードに送り込み、コンポーネントごとの設定ファイルを食わせてchef-soloを実行していました。

d.hatena.ne.jp

しかしこの運用はほんとうにツライものでした。

https://github.com/cloudfoundry-attic/vcap/blob/master/dev_setup/cookbooks/python/recipes/default.rb#L9-L11

たとえばChefのcookbook読むとこんな書き方が普通に行われています。

%w[ python-dev python-setuptools ].each do |pkg|
  package pkg
end

aptのリポジトリからpython-devやpython-setuptoolsが落とされてくるわけですが、何が起きるかというと「セットアップを流した時点での最新版が入る」わけです。つまり、昔構築した環境と、新しい環境では異なったバージョンがセットアップされている可能性が高い。

「でも、それが何か? 多少バージョン異なっても問題ないでしょ?」 って思われるかもしれません。でもそれは甘い。

https://github.com/cloudfoundry-attic/vcap/tree/master/dev_setup/cookbooks

これだけのCookbookがあり、それぞれのライブラリが複雑な依存関係を持っている。こうなると、結構高い頻度で依存関係のエラーが起きるんですよね。エラーでセットアップが止まってしまうのもツライし、その後原因特定もツライ。複雑に絡み合った依存関係の中から原因となっているパッケージとバージョンを切り分けて、問題が起きないように修正するという作業は、何も価値を生まない割には時間ばっかり消費する、できれば二度と経験したくないものでした。

BOSHはこういうトラブルが起きないよう、考え抜かれた仕組みになっています。

BOSHは導入の敷居が高く、あまり好ましく思わない人も多いのですが、じゃあたとえば同じ運用をChefでなくAnsibleでやれば上手くいくか?となると、おそらくダメでしょう。Chefの二の舞になって死ぬのが目に見えています。このあたりの運用を経験しないと、なかなかBOSHの良さって理解されないんですよね・・・。

Serviceの仕組み

CFはv1の頃から、今と変わらないServiceの仕組みを備えていました。

vmc create-service vmc bind-service vmc delete-service

一緒ですね。

しかしバックエンドの仕組みは微妙に異なりました。

ozalog.blogspot.jp

Cloud Controllerからのリクエストを受け取るService Proxyと、実際のバックエンドサービスがデプロイされているService Nodeに分かれており、Service ProxyとNode間はNATSで通信を行っていました。

現在のCFで利用されているService Brokerの考え方は、このService Proxyをより汎用的にAPI化したものです。Brokerがどういった形でバックエンドサービスをプロビジョニングするかは定義されおらず、好きに実装してくれというのが今の形です。

CF側でServiceを提供することしか考えられていなかったv1に対し、サードパーティーの提供するServiceも幅広くサポートしようという、エコシステムを意識して発展させた仕組みが現在のService Brokerといえるでしょう。

日本のコミュニティの誕生と今について

日本では2011/10/18に第1回 Cloud Foundry輪読会が開催されています。 当時CFの採用を検討していたNTTや楽天、富士通といった会社のメンバーが中心になっていますね。

atnd.org

また、2012年2月にはNTTをはじめ数社で日本Cloud Foundryグループが設立されています。

www.ntt.co.jp

ビジネス的な色合いの強い日本Cloud Foundryグループと、コードリーディングというディープ志向のCF輪読会。いきなりコミュニティの分断が起きてしまい、一体感を持った盛り上げ方が上手くいかなかったなーというのは振り返っても感じます。

その後日本Cloud Foundryグループは引き続き活動を続けており、関係するメンバーでCloud Foundry Tokyo meetupというものもやっています。

Cloud Foundry輪読会は、その後PaaS勉強会と名前を変え、今でも続いています。

2018年はCloud Foundry Container Runtimeの登場により、Cloud Foundryがカバーする範囲も大きく変わってきます。再度Cloud Foundryのコミュニティを活性化するよう、いろいろ活動していきたいなあと考える今日この頃です。

Cloud Foundry Container Runtimeでk8s運用

Kubernetes Advent Calendarの6日目〜

既にこのblogでは触れてしまっていますが、Cloud Foundry Container Runtime(以下CFCR)の話。

先日のKubernetes Meetup Tokyo #8でこんな発表をしました。

CFCRって何? PaaSとは違うの?

Cloud Foundryの名はついていますがPaaSではありません。

PaaSのCloud Foundryで培われた技術を応用して、Kubernetesクラスタを効率よく構築・運用できる仕組みです。

Cloud Foundryで培われた技術って何?

BOSHという仕組みがあります。

bosh

このBOSHを利用してk8sを構築運用するのがCFCRです。 BOSHの仕組みについてはこちらの17ページからを参考に。

https://www.slideshare.net/jacopen/cloud-foundry-container-runtimekubernetes#17

また日本Cloud Foundryグループの怪鳥 会長のozz さんが書いた、BOSH 101も参考になります。

speakerdeck.com

CFCRはどこで試せるの?

CFCRのドキュメントはこちら CFCR

現在のところ、AWS, GCP, vSphere, OpenStack向けのマニュアルが公開されています。

試した事例

makingさんのGCP, AWSでの構築事例

Kubo(Kubernetes on BOSH)をAWSにデプロイ - BLOG.IK.AM

Kubo(Kubernetes on BOSH)をGCPにデプロイ - BLOG.IK.AM

この記事が書かれたのは9月です。当時と概念的なものはあまり変わっていませんが、一部手順が異なる可能性はあるため、できれば公式ドキュメントをみながら構築を試みた方がよいでしょう。

ここらでひとつCFの昔話をしながら変遷を振り返る(その1)

Cloud Foundry Advent Calendar 2017の5日目〜

先日Facebook開いたら自分の5年前の投稿が。それはこのリンクの紹介でした。

www.ntt.com

懐かしい。前職はこのサービスの開発にがっつり携わっていたのですが、このときにベースにしていたのはCloud Foundryのv1でした。

それともう一つ。先日カサレアルさんが開催されたハンズオンセミナーでお話しさせて頂く機会を頂いたのですが、その際に「Cloud Foundryは2011年のV1から現在のバージョンに至るまで、唯一変わっていないものがある」 といった質問をしてみたんですよ。

答えとしては「cf push(vmc push)だけでアプリケーションのデプロイが出来る」だったのですが、そのときに頂いた答えの中に「コンテナ?」というものがあったんですよね。確かに今PaaSを一から作るなら、間違いなくコンテナの活用を考えるでしょう。

でも、最初のバージョンのCFってコンテナなんて使ってなかったんですよ。「え、じゃあどうやってマルチテナント実現してたの?」って思うかもしれません。

ということで、どのくらい需要があるのか分からないけれど、むかーしむかしのCFを紹介しながら、変遷を振り返ってみようかなと思います。

Cloud Foundryの登場

OSSとしてのCloud Foundryは2011年4月にVMwareから発表されました。

www.publickey1.jp

元々はCloud Foundry社をSpringSource社が買収し、SpringSourceをVMwareが買収したところから始まっています。 その後Pivotalが設立されるまでVMwareが開発を続けていました。

なおこれらCloud Foundry v1のコードはGitHubのcloudfoundry-atticに残っており、今でも全てのコードを確認することが出来ます。

github.com

でもたぶんセットアップしても動かないと思います。たぶん。

CFv1のアーキテクチャ

CFv1のアーキテクチャは非常にシンプル。新野さんのこちらの記事には当時のCloud Foundry輪読会の様子がまとまっています。

www.publickey1.jp

メッセージングバスのNATSがCloud Foundryの要。NATSは現在のCFにもありますが、ずっと広範囲に利用されていました。

Cloud ControllerやHealth Manager、DEA、Routerといったほぼ全てのコンポーネントがNATSに接続し、メッセージのやり取りを行っていました。 自立分散型のアーキテクチャでスケーラブル、にも関わらず現在に比べるとコンポーネント数も少なく、非常に理解しやすいアーキテクチャでした。

これはNATSの開発者であり、当時のCloud Foundryの開発をリードしていたDerek Collison氏(現在はApceraのCEO)の思想がダイレクトに反映されています。

ただ、コンポーネントはスケーラブルだけどNATSがクラスタ非サポートで単一障害点でした :p

認証・認可

全部Cloud Controllerが担ってました。 その後2012年に入り認証をUAA、認可をACMというコンポーネントに分離する考えが示され実装が進められましたが、結局実現したはUAAのみでACMの話はどこかに消え去りました。

labs-vcap-uaa/UAA-CC-ACM-VMC-Interactions.rst at master · mozilla/labs-vcap-uaa · GitHub

マルチテナント

冒頭にも書きましたが、CFv1にはコンテナはありませんでした。 じゃあどうやってマルチテナントを実現していたかというと、アプリケーションごとに異なるuidが設定され、ファイルのパーミッションもそのuidに向けて設定される・・・だけ・・・という、Linuxのユーザー管理に頼る仕組みでした。

f:id:jaco-m:20171205204240p:plain

uid異なるので他のアプリケーションにちょっかい出すことは出来なかったんですが、たとえば他のアプリがCPU食いつぶせばダイレクトに影響を受けます。

アプリからifconfigするとDEAのIP見えるし、ps打つと他にどんなアプリが上がっているか見ることもできてしまいました。

VMwareはcloudfoundry.comというパブリックPaaSもやっていたのですが、そこにifconfigを叩くだけのアプリを立ち上げ、ひたすら上げ下げを繰り返してIPアドレスを収集し、DEAの台数を調べる・・・なんてこともできちゃいましたね。

とはいえこのアイソレーションでは不十分というのは開発側も認識しており、コンテナに対応したDEAの開発も進んでいました。それがDEA_ngです。 DEA_ngでは当初LXCの利用も検討されていましたが、LXCは要求事項に対して機能がリッチすぎ、PaaSの利用用途としては過剰なものでした。そこで、Cloud Foundryチームはwardenとう独自のコンテナランタイムを作成し、DEA_ngに採用しました。

今でこそコンテナは当たり前になりましたが、Dockerが登場したのは2013年、大きく話題になりはじめたのが2014年です。一方この議論は2011年から進んでいます。このことからも、コンテナのムーブメントとは関係なく、それ以前からPaaSの一要素としてコンテナ技術が考えられていたことが分かるでしょう。

なおDEA_ngはCFv1では採用されることなく終わり、実際に使われ始めたのはCFv2になってからです。

www.slideshare.net

buildpack

CFv1にはBuildpackサポートはありませんでした。

ですが当時からRuby, Java, NodeJSなどマルチ言語対応していました。どうしていたかというと、Stagerと呼ばれるコンポーネント内にプラグイン形式で各言語ごとの設定方法が記述されていました。

github.com

なおBuildpackのような言語を自動検出する仕組みはStagerにはなく、クライアント側の判定ロジックで検出し、APIリクエストで言語を指定していました。

なお、2012年末からBuildpack対応のコミットが入り始めましたが、CFv1が収束に向かったため、このvcap-stagingのBuildpack対応は日の目を見ずに終わることになります。

つづく

どう考えても1記事にまとまりそうになかったので、残りは別記事として上げることにします。

  • CLI
  • CFv1のデプロイ方法からBOSHに至るまで
  • Serviceの仕組み
  • 当時の盛り上がりの話

あたりを書いてみようかなと考えています。

CFCRとCFARの使い分けの話

Cloud Foundry Advent Calendar1日目!

CF、Kubernetesやるってよ

10月のCloud Foundry Summit EUで、Cloud Foundry Container Runtimeが発表されました

これは今年の頭から始まったBOSHでKubernetesを構築するプロジェクト "Kubo"がリブランディングされたものになります。 KuboはPivotalとGoogleの共同プロジェクトとして進んでいましたが、今年の6月にCloud Foundry Foundationに寄贈されていました。

KuboがCloud Foundryの名を冠すことになり、これまで単にCloud Foundryと呼ばれていたApplication Platform(PaaS)のほうは、Cloud Foundry Application Rutime(以下CFAR)という名称に変更になります。

おやおやこれはどうしたことでしょう。 Cloud FoundryはついにPaaSを諦めてKubernetesに乗り換えたのか? なんて声も一部から聞こえてきそうです。

f:id:jaco-m:20171201211535p:plain

KubernetesがあるとこれまでのApplication Plaformは要らなくなっちゃうんでしょうか?

Kubernetesにしたところで簡単になるとは限らない

たとえば何らしかのアプリを開発して、世の中に公開することを考えてみましょう。

CFARならこうです。

$ cf push

簡単ですね。

じゃあKuberneteだとどうでしょう。

  1. Dockerfileを書く
  2. docker buildする
  3. docker pushする
  4. kubernetes manifest書く
  5. kubectl createする

この流れの中で、考えなければいけないこと、覚えなくてはいけないこと、結構ありますね。

Dockerfile書くのめんどくさい問題

先日のPivoatl.IO 2018のmakingさんの発表ではこんな話がありました。 f:id:jaco-m:20171201214632p:plain

それな。

自分も正直Dockerfile好きじゃないんですが。この例はめちゃくちゃシンプルなほうで、複雑なDockerfileになると数十行から百何十行になったりします。Dockerの挙動をあらかた理解した上で、さらに自分のアプリが上手く動くように記述していかなくてはいけない。 さらにうまくレイヤーが作られるように考慮するテクニックを求められる。 結果として、作ったアプリをデプロイしたいだけなのにDockerfileに詳しくならないといけない

プライベートリポジトリ用意しなきゃいけない問題

パブリックなDockerhubに上げられるならまだしも、表に出したくないイメージの場合何らしかのプライベートリポジトリを用意しないといけない。地味にこれもめんどくさい

k8s manifestツラい問題

これもう、ほんとツラいんですけど、アプリケーション開発者のうちどのくらいの人がこのk8s manifest書きたいと思ってるんだろうというのが気になります。 k8sの練習における定番であるguestbookですら、manifest見るとうへーってなりますね。 https://github.com/kubernetes/kubernetes/tree/master/examples/guestbook

もちろん毎回一から書くのでは無く、既にあるものからのカスタマイズというパターンが多くなると思いますが、やはりアプリケーションそのものに関わる作業ではないので、避けられるのならば避けたい作業の一つです。というか、作ったアプリをデプロイしたいだけなのにKubernetesのリソースに詳しくならないといけない。

アプリごとの最適化を自分で頑張らないといけない問題

これまたmakingさんの発表にもありました。

f:id:jaco-m:20171201223143p:plain

たとえばJavaであれば、ホストのCPUやメモリ量、アプリケーションに応じたパラメータのチューニングが必要なんですが、k8sを利用する場合そのあたりも自分で設定しかなければいけません。というのも、Dockerやk8sはコンテナを動かすための仕組みであって、その上で動くアプリの細かな事情についてはカバー外だからです。

Javaだから悪いというわけでもなく、たとえば Apache+mod_phpで動かすときにも、ApacheをpreforkにするのかとかMaxClientはどうかとか、そういった細かいチューニングを考慮していかなきゃいけないわけです。

じゃあCFARだとどうかというと、そのあたりは基本自動でやってくれます。 なぜならCFARはアプリケーションを動かすために作られた仕組みだからです。Buildpackがうまいことそのあたり設定してくれます。

アプリを開発・運用するならやっぱりCFAR

ということで、もしあなたがアプリケーション開発をしており、それの運用を楽にしたいということでプラットフォームを選ぶのなら、基本CFARのほうが幸せになれます。大体の面で楽ができます。

インフラの柔軟性が必要ならCFCR

じゃあCFCRはどういうときに使うのかというと、身も蓋もない言い方をするとCFARでうまく動かせなかったものを動かす用途になるかなと考えています。 たとえばCFARでRedisをキャッシュに使いたいとか、手っ取り早くMySQLのコンテナ立ち上げて繋ぎにいきたいとか。 こういったstaticなデータを持つものはCFAR上では動かすことができないため、CFCRで上げるというのは選択肢のうちに入ってくると思います。もっとも、AWSやAzureなどを利用している場合は、そのあたりはマネージドなサービス使った方が良いとは思いますが。

また、Persistent Storageがどうしても必要なアプリケーションの場合も、やはりCFCRを使った方が上手く運用できるかと思います。 Persistent StorageはCFARもNFSに対応していますが、Kubernetesはブロックストレージ含めてさまざまなストレージに対応しているため、そこの点はCFARに比べて明確なメリットがあります。

さいごに

個人的にはこんな感じの使い分けでやっていこうかなと考えています。 CFCRはこの執筆時点での最新バージョンは0.9.0です。 おそらくそう遠くないうちに1.0が出ると思いますので、そろそろ本気で活用しても良い時期なのかな、と考えています。

Cloud Foundry Advent Calendarやります

ちょう久々にCloud Foundry Advent Calendarやります!

qiita.com

自分自身も記憶が曖昧だったんだけど、Cloud Foundry Advent Calendarやったの2013年が最後なんですよね。2014年とか15年はOpen PaaSと間口を広げて開催したので。

adventar.org

ただ、今年はCloud Foundry Container Runtimeもありーの、BOSH v2もありーのでCloud Foundry特化でも結構ネタが書けるんじゃないかなと思いまして。自分自身も転職により、よりCFに近い立ち位置になりましたので、改めてAdvent Calendarをやってみようと思った次第。

というわけで、CFに関わっている方も、趣味でやっている方も、利用者として使われている方も、気軽に参加していただければと思います。 難しい内容でもライトな内容でも大歓迎です!