Slide 01
Slide 02
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480
Spacer640x480

Chef ベーシックトレーニング

Chefをこれから触ってみようという人向けのベーシックトレーニングの資料です。フィードバックは@ryuzeeまで

1. Chef ベーシックトレーニング 2016年4月 RYUZEE.COM
2. RYUZEE.COMについて ✤ アジャイル開発/DevOps/クラウドに関する 従量課金型コンサルティングサービスを提供 ✤ http://www.ryuzee.com @ryuzee
3. 本トレーニングの対象 / 想定 ✤ [対象] インフラ構築自動化の経験があまりない方 ✤ [対象] とりあえず簡単にChefがどんなものか触って確認したい方 ✤ [対象外] ガッツリとハンズオンで色々試したい方 (Chef社のサイトなどを 参照して自習してください) ✤ [想定] 所要時間を2-3時間に設定したコンテンツになっており、全てはカ バーしていません。より詳細を学習したい場合はChef社のサイトや関連書 籍をご利用ください
4. 更新履歴 ✤ 2016/4/9 Attribute/Role/Environmentの説明を追加 ✤ 2016/4/3 Vagrant1.8系でスナップショット機能がついたためSaharaの インストールを廃止 ✤ 2016/4/1 初版作成
5. DevOpsとは何か?
6. 現在の状況 ✤ ビジネスの変化がどんどん早くなっている ✤ ITがビジネスの ✤ 良いソフトウェアを顧客に届けることはビジネスにとって必須 ✤ 一方、特にトラディショナルな企業や大企業では、デリバリの速度はとて も遅く、間違いやすい方法でやっている ✤ これはビジネス機会や売上の損失に繋がる ✤ 他にも問題がおこるかもしれない ✤ ITがボトルネックになることがよくある に
7. ムダ Always 7% ✤ ソフトウェアの機能のうち64%は、 Some6mes 16% Never 45% O"en 13% ほとんど、もしくは全く使われてい ない (Standish Group Chaos report 2002). ✤ 自分のパソコンにプリインストール Rarely 19% されているソフトウェアを考えれば イメージがつくはず
8. 7つのムダ ✤ 作りすぎのムダ ✤ 手待ちのムダ ✤ 運搬のムダ ✤ 加工のムダ ✤ 在庫のムダ ✤ 動作のムダ ✤ 不良をつくるムダ
9. 何が正しいのか、未来に何がおこるのかを事前に知るのは難しい。 早い変化に対応できる能力があることが重要。
10. 素早いフィードバックサイクルをつくる This is not only for Learn Bu il d s a e M e r u
11. DevとOpsのコンフリクト ✤ 役割や責任の違い (誰がそれを決めたのか、思い込みでは?) ✤ 「それは自分の仕事ではありません」 (そんなこと言うのは誰だ?) ✤ サイロ化 ✤ これらがオーバーヘッドをつくりだしビジネスの速度を遅くする
12. ✤ OpsはDevのように考 える ✤ DevはOpsのように考 える
13. Werner Vogels, CTO, amazon.com You build it, You run it
14. DevOpsが目指すところ ✤ DevOpsが意図するのは、文化とツールを活用して、ビジネス上の結果を 達成すること、ビジネスのアジリティをあげること、そしてリスクを減ら すこと。
15. DevOpsの5つの側面 ✤ Culture (文化) ✤ Lean (リーン) ✤ Automation (自動化) ✤ Measurement (測定) ✤ Sharing (共有)
16. Infrastructure as Codeがなぜ必要なのか?
17. 手作業によるプロビジョニングの課題 ✤ 対象サーバが増えるとそれだけプロビジョニングの時間が増える ✤ 手順書やチェックリストがメンテナンスされない・最新に保たれない ✤ 手順書を使って手作業しても間違える ✤ ドキュメントは他のプロジェクトで再利用しにくい
18. Infrastructure as Codeの利点 ✤ プロビジョニングにかかる時間は台数が増えてもほぼ一定 ✤ コード=手順書となるのでコードだけを最新に保てばよい ✤ コードは書いたとおりに動作する。同じコードを使えば同じサーバができ あがる(ように書く) ✤ コードはCIツールを使って継続的にテストできる ✤ 再利用性が高い
19. どのようにインフラ構築を自動化するか
20. 自動化のいくつかの方法 ✤ シェルスクリプト ✤ Capistranoなどのデプロイツール ✤ Chef / Puppet / Ansibleなどのプロビジョニングツール
21. シェルスクリプト #!/bin/sh yum install -y httpd httpd-devel php phpmbstring php-pdo php-mysql mysql-server ✤ 一番単純なやり方 /sbin/chkconfig --level 2345 httpd on ✤ ただし制御構文が多数含ま れていると保守しにくくな るという課題がある /sbin/chkconfig --level 2345 mysqld on /etc/rc.d/init.d/mysqld start /etc/rc.d/init.d/httpd start
22. デプロイツール(Capistrano) task :install_amp, roles => :web do ✤ Capistranoやデプロイツー ルは通常アプリケーション のデプロイ用に作られてい る ✤ インフラ構築に利用するこ とはもちろん可能だが、シェ ルスクリプトを埋め込むよ うな形では大した利点なし run <<-CMD sudo yum install -y httpd httpd-devel php phpmbstring php-pdo php-mysql mysql-server && sudo /sbin/chkconfig --level 2345 httpd on && sudo /sbin/chkconfig --level 2345 mysqld on && sudo /etc/rc.d/init.d/mysqld start && sudo /etc/rc.d/init.d/httpd start CMD end
23. プロビジョニングツール(Chef) %w{httpd httpd-devel php php-mbstring php-pdo php-mysql mysql-server}.each do ¦p¦ package p do action :install end end service "httpd" do action [:enable, :restart] supports :status => true, :start => true, :stop => true, :restart => true end service "mysqld" do action [:enable, :restart] supports :status => true, :start => true, :stop => true, :restart => true end
24. プロビジョニングツールの比較 Chef Ansible Puppet DSL (Rubyベース) DSL DSL Client / Server (Agent) Agentless Client / Server (Agent) 管理用のツールがすくない かなり前に開発されたもので既 に非主流といえる 単純で学習すべきことは少ない 独自DSLを学習する必要あり knife, berkshelf, foodcriticなどの 多数の関連ツールあり DSL(Rubyベース)の学習が必要 ✤ Rubyで書かれた多くのインフラ関連のツールがあるため、インフラエンジニア でもRubyを書けるようになっておくと良い(Go言語も主流化しつつある)
25. Chefのアーキテクチャ
26. アーキテクチャ ✤ 基本的には Client / Server 型 ✤ 全ての情報はChef Serverに保存される。全て のノードはChef Clientを経由してChef Server にアクセスし、それによってCookbookや Attributeなどを取得し適用する
27. 基本的な用語 #1 ✤ Chef Server => Chef Serverはハブのような形で、Cookbookやポリ シーなどを保存するとともに、各ノードのメタデータも保存する ✤ ノード => ノードとは物理や仮想やクラウドやネットワーク機器のマシン を指す。Chefで管理するにはChef Clientのインストールが必要 ✤ Chef Client => ノードにインストールするツールで、サービスとして動 作させることもコマンドラインツールとして動作させることも可能
28. 基本的な用語 #2 ✤ Cookbook => Cookbookはプロビジョニングに必要なファイル一式を まとめたもので、レシピ(Recipe)、アトリビュート(Attributes)、テンプ レート(Templates)、拡張などを含む。この単位で配布したり管理する ✤ レシピ => 対象のノードを設定するためのDSL(Rubyベース)のコード。1 つのCookbookには複数のレシピを含むことができる
29. 注意: Chef Solo ✤ Chefには、Chef Soloと呼ばれる非Client/Server型のモードもあります (ありました) ✤ が現時点では非推奨となっており今後廃止される可能性があります ✤ Chef ServerなしでChefを実行したい場合は、Chef Local Mode を使 うことになります。そのためのツールとしてknife-zeroが利用可能です ✤ 多くのWebサイトや書籍にChef Soloの記述がありますが、上記について 認識しておくようにしてください
30. ハンズオンの環境
31. 環境の全体像 ホスト名: development ホスト名: node01 IPアドレス: 192.168.33.10 IPアドレス: 192.168.33.200 OS: Ubuntu 14.04 Chef-DK / Docker / vi / vim / emacs OS: Ubuntu 14.04 Chef Clientインストール済み この環境にログインして作業 Development この環境に適用される Node01 Vagrant: HashiCorp提供のオープンソースの開発環境管理ツール VirtualBox: Oracle提供のオープンソースの仮想化ツール 自分の端末
32. https://www.virtualbox.org/ よりダウンロードしインストール
33. https://www.vagrantup.com/ よりダウンロードしインストール。 既にインストール済みの場合は1.8以上で あることを確認し必要なら更新する
34. Vagrantの基本 ✤ Vagrantは開発環境の構築・管理ツールの中でもっとも有名なオープンソー ス製品。HashiCorpが中心となって開発が進んでいる ✤ VagrantではVirtualBoxの仮想マシン、Dockerのコンテナ、AzureやAWS の仮想サーバなどを扱える。Vagrantがそれぞれの差を吸収していると考 えると分かりやすい ✤ Vagrantfileが環境を定義したもの。同一のVagrantfileからは同一の環境 ができる。チームで共用すれば全員同じ環境が手に入るので開発する上で メリットが非常に大きい
35. Vagrantfileの例 Vagrant.configure(2) do ¦config¦ config.vm.define :development do ¦development¦ development.vm.box = 'ubuntu-14.04.4-chef-training-development-kit' development.vm.hostname = 'development' development.vm.network 'private_network', ip: '192.168.33.10' end config.vm.define :node01 do ¦node01¦ node01.vm.box = 'ubuntu-14.04.4-chef-training-node' node01.vm.hostname = 'node01' node01.vm.network 'private_network', ip: '192.168.33.200' end end http://bit.ly/224TbdH よりダウンロード可能
36. Vagrantの組み込みコマンド例 # boot virtual machines vagrant up # stop machines vagrant halt [machine name] # boot specified machines vagrant up development # dispose machines vagrant destroy [machine name] # login to the specific machine vagrant ssh development # add box as a template vagrant box add box_name box_url # reboot machines vagrant reload [machine name] # install plugin vagrant plugin install plugin_name
37. Boxの追加 ✤ ターミナルまたはコマンドプロンプトで以下のようにboxを追加します vagrant box add ubuntu-14.04.4-chef-training-development-kit http://bit.ly/1W4FWtV vagrant box add ubuntu-14.04.4-chef-training-node http://bit.ly/1PQjMEl
38. 全ての準備が終わったら… vagrant up ✤ Vagrantfileを配置したディレクトリにて、上記コマンドをターミナルまた はコマンドプロンプトにて実行 ✤ 仮想マシンが2台立ち上がるはず ✤ 起動に失敗した場合はbox名のタイポなどエラー出力を確認します
39. 最初のCookbookを作ってみる
40. nginxのインストールを自動化する ✤ nginx [engine x] は(言うまでもなく)、HTTPおよびリバースプロキシサー バのプロダクト。Apache HTTP Serverよりも性能面で優位 ✤ これからChef経由でnginxをインストールします ✤ まずは、 development 環境にログインします。ターミナル(OS X)または コマンドプロンプト(Windows)で vagrant ssh development と入力 します
41. 開発環境へのログイン ✤ 以下のようなメッセージが表示されることを確認してください ✤ これでUbuntuの仮想マシン内の開発環境にいることになります ✤ ユーザー名はvagrantでカレントディレクトリは/home/vagrant Welcome to Ubuntu 14.04.4 LTS (GNU/Linux 4.2.0-27-generic x86_64) * Documentation: https://help.ubuntu.com/ Last login: Fri Apr 1 20:54:29 2016 from 10.0.2.2 vagrant@development: $
42. gitの設定 ✤ ハンズオンを始める前に以下のようにgitの設定をします git config --global user.name Sushi Taro git config --global user.email taro@example.com
43. Repositoryの作成 ✤ 最初にCookbookやノード情報を保存するためのRepositoryを作成しま す。以下のコマンドを実行します chef generate repo chef-repo cd chef-repo
44. コマンドの実行結果 Installing Cookbook Gems: Compiling Cookbooks... Recipe: code_generator::repo * directory[/home/vagrant/chef-repo] action create (up to date) * template[/home/vagrant/chef-repo/LICENSE] action create_if_missing (up to date) * cookbook_file[/home/vagrant/chef-repo/.chef-repo.txt] action create_if_missing (up to date) * cookbook_file[/home/vagrant/chef-repo/README.md] action create_if_missing (up to date) (snip) Recipe: code_generator::repo * cookbook_file[/home/vagrant/chef-repo/cookbooks/README.md] action create_if_missing (up to date) * execute[initialize-git] action run - execute git init . * template[/home/vagrant/chef-repo/.gitignore] action create_if_missing - create new file /home/vagrant/chef-repo/.gitignore - update content in file /home/vagrant/chef-repo/.gitignore from none to 3523c4 (diff output suppressed by config)
45. ディレクトリ構造 ✤ tree -L 2 コマンドを実行すると右図 のようなディレクトリ構成が表示され ればOKです ✤ この中にcookbooksディレクトリが あることが分かります。ここに cookbookを保存します vagrant@development: /chef-repo$ tree -L 2 . ¦-- chefignore ¦-- cookbooks ¦ ¦-- example ¦ `-- README.md ¦-- data_bags ¦ ¦-- example ¦ `-- README.md ¦-- environments ¦ ¦-- example.json ¦ `-- README.md ¦-- LICENSE ¦-- README.md `-- roles ¦-- example.json `-- README.md 6 directories, 9 files
46. nginx cookbookの作成 ✤ knife cookbook create nginx -o ./cookbooks/ コマンドを実行 してください。これでcookbookの ディレクトリや必要なファイルを自 動で生成します ✤ 右図のような構造になっていること を確認してください vagrant@development: /chef-repo$ tree -F 2 ./cookbooks/ nginx/ 2 [error opening dir] ./cookbooks/nginx/ ¦-- attributes/ ¦-- CHANGELOG.md ¦-- definitions/ ¦-- files/ ¦ `-- default/ ¦-- libraries/ ¦-- metadata.rb ¦-- providers/ ¦-- README.md ¦-- recipes/ ¦ `-- default.rb ¦-- resources/ `-- templates/ `-- default/ 10 directories, 4 files
47. cookbookの実装 ✤ ✤ ./cookbooks/nginx/recipes/ default.rbを好きなエディタで開き、 右図のテキストを入力します これはnginxのパッケージをインス トールし、サービスを有効化・起動 することを意味しています package 'nginx' do action :install end service 'nginx' do action [ :enable, :start ] end
48. Chef Clientの設定 knife zero bootstrap 192.168.33.200 -x vagrant --sudo --ssh-password vagrant ✤ このコマンドによって設定対象のノードにChef Clientをインストールし つつ必要な情報を取得して保存します ✤ コマンド実行後、 nodes と clients ディレクトリが/home/vagrant/ chef-repo/ 以下に作成されていることを確認してください
49. 対象ノードの登録確認 knife node list -z ✤ 上記のコマンドを実行して node01 が表示されればOKです ✤ 複数のノードを扱っている場合はノード数分表示されます knife node show node01 -z ✤ 上記のコマンドを実行して node01 の詳細情報を表示できます
50. run_listの設定 knife node run_list add node01 'recipe[nginx]' -z ✤ このコマンドは、node01という名前のノードにnginxクックブックの defaultのレシピを適用するように設定することを意味しています。 ✤ このコマンドによって nodes/node01.json のファイルが更新されます。 ファイルの末尾のrun_listに追加されていることを確認してください ✤ 同時に複数のレシピを適用することももちろんできます
51. VagrantでSnapshotの取得 vagrant snapshot save node01 node01_001 ✤ 上記のコマンドをホスト側(仮想マシン側ではない)で実行します ✤ これはvagrantの組み込みコマンドであるshanpshotを使って、現在の仮 想マシンの断面を保存しています。これによってあとから変更を簡単に戻 せるようになります ✤ 待ち時間を短縮するために、その他いろいろなツールを活用するように普 段から工夫していきましょう
52. 対象ノードに変更を適用 knife zero converge 'name:node01' -x vagrant --sudo -a knife_zero.host --ssh-password vagrant ✤ 上記のコマンドを実行すると、node01にnginxのレシピが適用されます。 Chefでは、このことをノードが指定した状態に収束(Converge)したと いいます ✤ ブラウザで右記のURLにアクセスしてください http://192.168.33.200
54. ここまで大丈夫ですか? ✤ ここまで正常に動作したのであれば、作成したファイルをバージョン管理 します git add * git commit -m initial commit ✤ もしうまくいかない場合はエラーが出力されているはずなので内容を確認 します
55. Template #1 ✤ ✤ templateというリソースを使うこと で、ファイルを生成して配置するこ とができます。 index.htmlを変更してみます。 index.html.erb というファイルを cookbooks/nginx/templates/ default/ に配置してください。内 容は右記の通りです <!DOCTYPE html> <html> <head> <title>Welcome to nginx!</title> </head> <body> <h1>Welcome to Chef Training</h1> <p><%= node.name %></p> </body> </html>
56. Template #2 ✤ 次にレシピを修正します ✤ cookbooks/nginx/recipes/ default.rbを開き、右図のハイライ トした箇所を追加します ✤ 収束させる前に、一度 vagrant snapshot restore node01 node01_001 として対象ノードの 状態を元に戻しておきましょう package 'nginx' do action :install end template 'index.html' do path '/usr/share/nginx/html/index.html' owner root group root mode 0644 end service 'nginx' do action [ :enable, :start ] end
57. 対象ノードに変更を適用 (再) knife zero converge 'name:node01' -x vagrant --sudo -a knife_zero.host --ssh-password vagrant ✤ 上記のコマンドを実行すると、node01にnginxのレシピが適用されます。 Chefでは、このことをノードが指定した状態に収束(Converge)したと いいます ✤ ブラウザで右記のURLにアクセスしてください http://192.168.33.200
59. Resource ✤ ここまででクックブックの中で、 package , service , template とい うキーワードを使ってきました。これらのキーワードのことをChefでは Resource と呼びます ✤ Chefには多くの組み込みResourceがあります(次ページ参照) ✤ これらのresourceを組み合わせることでcookbookを作成していきます
60. Resource (抜粋) package user powershell_script ifconfig template group ruby_block http_request service remote_file cron link file execute git log directory script mount chai
61. 基本的な用語 #3 / さらに学習すべきこと ✤ Attribute => Attribute(s)とはプロビジョニングの際に使える変数のこと。たとえば、 PHPの環境をつくるときにphp.iniの設定項目の値を環境によって変えたいとします。 そのとき外部から値の変数を渡すことができます。 ✤ Role => ロールを定義することができます。たとえばWebサーバロール、DBサーバ ロールといった形です。ロールの中には複数のレシピを含めたりAttributeを設定した りできます。ロールを使うことである用途のインフラを単純にロールを設定するだけ で構築することができます。 ✤ Environment => 例えば開発環境・ステージング環境・本番環境といった複数の環 境を定義できます。EnvironmentごとにAttributeの値を変えることもできるので、 接続先や通知先といったものを環境ごとに分けられます。
62. テスト自動化
63. なぜテスト自動化が大事なのか? ✤ リスク低減 ✤ 手作業のプロセスを減らす ✤ いつでもどこでもデプロイ可能にする ✤ プロジェクトの可視性をあげる ✤ 信頼性をあげる
64. Test Kitchen ✤ Test Kitchenはcookbookを独立した環境で実行しテストするためのテス トハーネス ✤ 詳しくは公式サイトを参照 http://kitchen.ci ✤ Test Kitchenは独立した環境(例えばVagrant, Docker, AWS, Azure…)を 立ち上げ、指定したレシピを適用し結果を評価します ✤ IBats, shUnit2, RSpec, Serverspecなどのテストフレームワークが利用 できます
65. http://serverspec.org/
66. 準備 ✤ Test Kitchenにはジェネレータが用意されています。以下のコマンドを実 行してください cd /home/vagrant/chef-repo/cookbooks/nginx kitchen init -D kitchen-docker ✤ .kitchen.yml, chefignore, test/integration/defaultなどが作成されます mkdir -p test/integration/default/serverspec/localhost
67. テストの作成 require 'spec_helper' describe package("nginx") do it { should be_installed } end describe service("nginx") do it { should be_enabled } it { should be_running } end test/integration/default/serverspec/ localhost/default_spec.rb test/integration/default/serverspec/ spec_helper.rb describe port(80) do it { should be_listening } end describe file( /usr/share/nginx/html/index.html ) do it { should be_file } end require 'serverspec' set :backend, :exec
68. テストの意図は何か? require 'spec_helper' ✤ nginxのパッケージがインストールされている describe package("nginx") do it { should be_installed } end describe service("nginx") do it { should be_enabled } it { should be_running } end describe port(80) do it { should be_listening } end describe file("/usr/share/nginx/html/index.html") do it { should be_file } end こと ✤ nginxのサービスが動作していること ✤ nginxのサービスがサーバ起動後に起動するこ と ✤ nginxがTCP80番ポートでListenしていること ✤ index.htmlが指定場所にあること
69. 設定ファイルの編集とテスト実行 --driver: name: docker provisioner: name: chef_solo platforms: - name: ubuntu-14.04 suites: - name: default run_list: - recipe[nginx::default] attributes: ✤ .kitchen.ymlを右記の内容に変更する ✤ これはUbuntu14のDockerマシンを起 動してテストすることを意味します ✤ kitchen test と実行するとテストが始 まります ✤ テストには数分時間がかかります
70. テスト結果はこのような形になります
71. Jenkinsを使ってテストを実行する ✤ CookbookのテストをJenkinsに実施させることはもちろん可能です ✤ 興味があれば試してみてください ✤ なおJDK8 (JDK7はNG)とJenkinsのインストールは以下のように実行します sudo add-apt-repository ppa:openjdk-r/ppa sudo apt-get update sudo apt-get install openjdk-8-jdk wget http://pkg.jenkins-ci.org/debian-stable/binary/jenkins_1.642.4_all.deb sudo dpkg -i jenkins_1.642.4_all.deb
72. よいCookbookを書くには?
73. コミュニティCookbook ✤ Chefには大きなエコシステムがあり、以下のようなCookbookがコミュニティ からリリースされています。詳細は右記参照 https://supermarket.chef.io/ mysql nginx apache2 postgresql java git apt yum php build-essential nodejs mongodb ntp jenkins database python docker tomcat rabbitmq elasticsearch
74. Berkshelf : 依存関係の管理 ✤ 特にコミュニティCookbookにおいては、ほかのCookbookに依存してい ることがあります ✤ この課題を解決するために使うのがBerkshelfです。詳細は公式サイトを 確認してください http://berkshelf.com/ ✤ Berkshelfは他の言語のパッケージマネージャ、たとえば composer(PHP), bundler(Ruby) and npm(Nodejs)のChef版と考えて ください
75. コードをクリーンに保つ ✤ Cookbookは手順書と同等になります。したがって可読性や保守性は非常 に重要です(もちろん継続的インテグレーションも重要です) ✤ たとえば、Foodcriticを使うことで例えばRubyのRubocopのような Cookbookの静的解析が可能です ✤ 単一責務の原則にしたがってCookbookを小さいサイズに保つようにして ください
76. 質問?
No comments...
272013
Attractor Inc. Founder / CTO / Agile Coach / Certified Scrum Professional / Certified ScrumMaster / Certified Scrum Product Owner Twitter : @ryuzee Web : https://www.attractor.co.jp/ Web : http://www.ryuzee.com/

Related Slides