Page List

Search on the blog

ラベル インフラ の投稿を表示しています。 すべての投稿を表示
ラベル インフラ の投稿を表示しています。 すべての投稿を表示

2021年5月9日日曜日

ecsとasgを使ってオートスケールするサービスをterraformで構築する

 GWの自己研鑽最終日です。前回試したCapacity Providerを用いたコンテナインスタンスのAutoScaleとECSサービスのAutoScaleをterraformでやってみました。
  • すでにterraformを書いている人たちがいたので、まずはそれをリファレンスと照らし合わせながら読んで理解するところから始めた
  • terraformを書いた
    • ググると二種類のAutoScaleのどちらかをterraform化したものは出てくるのだが、どちらもやっているのは見当たらなかったので書いてみた
    • terraformのファイルのprefixに番号をつけておくと、何から作っていったのかがわかりやすくていいかもと思った
    • vpcまわりをterraformで書くのは初めてだった
    • assume roleは雰囲気しか理解してなかったが、何をするものなのかが分かった
  • 負荷をかけたり、かけなかったりして、スケールイン・スケールアウトされる様子を確認した
    • サービスのオートスケールに連動して、タスクが利用するコンテナインスタンスもオートスケールするのは地味に感動した

2021年5月7日金曜日

ecsとasgを使ってオートスケールするサービスを立ち上げる

  GWの自己研鑽4日目のメモです。

AWS ECS(EC2起動)でのAuto Scalingまわりの調査&検証をしました。

  • サービスの Auto Scaling
    • 公式ドキュメントを読んだ
      • ECSはサービスのリソース使用率(CPUやメモリの使用量)メトリクスをcloudwatchに発行している
      • このメトリクスを利用して自動的にサービスのスケールイン・スケールアウトをすることができる
    • ターゲット追跡スケーリングをやってみた
  • コンテナインスタンスの auto scaling
    • EC2起動の場合はサービスをホストしているコンテナインスタンスのauto scalingも考慮する必要がある。
    • 公式ドキュメントを読んだ
      • Capacity Providerというものを使うといいらしい
    • Capacity Provider = クラスタ中のタスクが利用するインフラを管理するやつ
      • target capacity(0~100)を定義するとその値をターゲット追跡してくれるらしい
      • 例えば100と設定するとクラスタ内にあるコンテナインスタンスのサービス使用率が100に近くなるようにscale-out/scale-inが行われる
    • Capacity Provider Strategy = どのCapacity Providerを使ってタスクのインフラを管理するかを決める戦略
      • クラスタは複数のCapacity Providerを持つことができるので、サービスを作るときにどの戦略でいくか選ぶ
      • 最低でもX個のタスクはCapacity Provider Aを使う(base値)、全体のうちY%のタスクはCapacity Provider Bを使う(weight値)というような戦略を作ることができる
    • Default Capacity Provider Strategy = デフォルトのCapacity Provider Strategy
      • サービス起動時にCapacity Provider Strategyを指定しなかった場合に使われる戦略。
      • クラスタごとに決めることができる
    • Classmethodの記事を参考に実際に動かしてみた


2021年5月5日水曜日

ビルドしたamiを使ってecsクラスタを起動する(EC2起動)

 AWSのお勉強の続きです。

前回ECS Optimized AMIをベースに作ったカスタムAMIをクラスタとして起動して、ECSを動かしました。

  • EC2起動のECSのgetting-startedをやってみる
  • ECSコンテナインスタンス = ECSコンテナエージェントを実行していて、ECSクラスタに登録されているインスタンスのこと
  • ECSコンテナインスタンスには Amazon ECS コンテナインスタンス IAM ロールが必要
  • まず空のECSクラスタを作成する
    • クラスタテンプレート「EC2 Linux + ネットワーキング」から作成しようとすると、最新のECS Optimized AMI以外は利用できないっぽい
  • 次にECSコンテナインスタンスを起動する
  • 起動したECSコンテナインスタンスをクラスタに登録する
  • バインドマウントでEC2インスタンスのライフサイクルに関連づけたデータをマウントする
  • fargate実行の場合はawslogsドライバーでcloudwatchにログストリームを送っていたが、ec2実行の場合はサーバにログインしてdocker logsすればログが見れる
  • シンプルにシステム運用する場合はfargate実行、社内に標準環境や共通のミドルウェア基盤などがある場合はAMIを作ってec2実行、という使い分けになりそう

2021年5月3日月曜日

packer&ansibleを使ってamiをビルドする

 GWの自己研鑽の続きです。

職場ではAMIの作成まわりは別のチームの人が担当しているので、自分でpackerを使うのは初めてでした。初歩的なことをやってみただけですが、雰囲気だけでも掴めて良かったです。

  • 公式サイトの aws-get-started をやってみた
    • 新しいバージョンではHCLが使えるらしい
    • 作成したリソースを削除し忘れないように注意!
      • サービス - EC2 - AMI から登録解除
      • サービス - EC2 - スナップショットから関連するスナップショットを削除
  • HCLを書くための環境を整える
    • IntelliJ に HCL プラグインを入れる
  • ECSをEC2起動するために使うカスタムAMIを作成する
    • Amazon Linux2 の ECS Optimized AMI をベースに作ることにした
      • 対象のAMI名は以下のコマンドで探せるっぽい
      • aws ssm get-parameters --names /aws/service/ecs/optimized-ami/amazon-linux-2/recommended --region ap-northeast-1
    • ansible provisioner の設定を追加する
      • ansible-local を使うとリモートホスト上で直接 ansible を実行できる
      • ansible-local を使うためにはリモートホスト上に ansible をインストールしておく必要がある
      • とりあえず ECS から mount するようのログディレクトリを追加してみた
  • 今日の進捗

2021年4月29日木曜日

ecsで簡単なサービスを立ち上げる(Fargate起動)

GWの自己研鑽の作業メモです。

  • 公式サイトのgetting-startedをやってみた
    • Fargateを使うとサーバーの管理が不要なので便利!
  • 適当なアプリを作ってecrにpushした
    • getting-started では Docker Hub にある既存の image を使っている
    • 自作の image を使ってみたかったので、テキトーな image を作った
    • docker や ecr まわりの丁寧な説明が公式ドキュメントにある
  • ecrにpushしたimageを使ってサービスを実行した
    • クラスタ、タスク定義、サービスを作った
  • タスクとサービスの違いが曖昧だったが違いが分かった
    • タスク = どの image でどのプログラムを実行するかを定義
    • サービス = どのタスクをどのクラスタで動かすか、デプロイ戦略はどうするか、タスクを何個動かすか、負荷分散はどのようにするかを定義

今年のGWはちゃんと勉強するよ〜

  今年はコロナで海外にも行けないし、帰省もできないので、インフラまわりの勉強をします。aws ecsの知見をえるために、以下の5ステップを少しずつやっていきます。

  1. ecsで簡単なサービスを立ち上げる(Fargate起動) 
  2. packer&ansibleを使ってamiをビルドする 
  3. ビルドしたamiを使ってecsクラスタを起動する(EC2起動) 
  4. ecsとasgを使ってオートスケールするサービスを立ち上げる 
  5. ecsとasgを使ってオートスケールするサービスをterraformで構築する

2020年4月29日水曜日

GCP MPI Cluster

 昔Distributed Code Jamというコンテストがありました。単一のマシンでは解けないような問題を複数のマシンでいい感じに解くというコンテストですが近年は開催されておりません。Distributed Code Jam のような問題を解いて遊びたいなと思い、手軽に並列コンピューティングを行う環境を構築できる仕組みを作ってみたのでブログで紹介したいと思います。

やりたいこと
ローカルマシンからコマンドを実行するだけで以下のことができるようにします。
  • 並列コンピューティング環境が自動構築される
  • 複数ノード上で目的のプログラムをコンパイルできる
  • 複数ノード上で目的のプログラムを実行できる
つくったもの
https://github.com/Kenji-H/gcp-mpi-cluster (このブログを書いているときはv0.9.1のものが最新です)

クラウドサービスに Google Cloud Platform、インフラの構築自動化に Terraform、構成管理ツールに Ansible、並列コンピューティングのライブラリに MPI を使っています。

Getting Started

0. Google Cloud Platform(GCP)のアカウントを持っていない場合は作成してください。また、ローカルマシンにTerraform、Ansible、jq が入っていない場合はインストールしておいてください。

1. GCPのコンソール画面から「Compute 管理者」ロールを付与したサービスアカウントを作成します。

2. サービスアカウントキーを生成し、terraform ディレクトリ直下に account.json という名前で保存します。

3. terraform/terraform.tfvarsというファイルを作成し環境設定をします。YOUR_PROJECT_NAMEのところはあなたのGCPプロジェクトIDに置き換えてください。日本で動かす場合はYOUR_REGION_NAMEのところはnortheast1、YOUR_ZONE_NAMEのところはasia-northeast1-aなどとするとよいでしょう。
project = "YOUR_PROJECT_NAME"
region = "YOUR_REGION_NAME"
zone = "YOUR_ZONE_NAME"

4. ./creater_cluster を実行します。このスクリプトはGCPのcompute engineを複数台起動し、並列コンピューティングに必要な環境設定を自動で行います。

5. ./compile hello でサンプルプログラムをコンパイルします。このスクリプトはローカルマシン上のプログラムをコンピューティングクラスタのノードに転送し、各ノード上でコンパイルを行います。

6. ./run hello でプログラムを実行します。hello は各ノードのプロセッサ名を表示するだけの簡単なプログラムです(app/hello/のソースを参考)。もう少し難しいプログラムを動かしたい場合は app/divisor のソースを見て hello と同様にコンパイル・実行してみてください。

7. 遊び終わったら ./destroy_cluster を実行して、インスタンスを破棄しておきましょう。

注意
このプロジェクトによって発生した如何なるエラー、問題、結果について責任を負いません。意図的に悪意のあるコードは含まれていませんが、利用にあたってはクレデンシャル情報(account.json)が外部に漏れないこと、また、インスタンスを起動しっぱなしにして高額請求されることのないように十分気をつけてください。

2017年10月21日土曜日

単一障害点とは

まえがき
システム全体のアーキテクチャを考えるときに、「単一障害点」という概念が大事らしい。
意味は一目瞭然だけど、大切な概念っぽいので調べてみることにした。

語句の意味
その単一箇所が働かないと、システム全体が障害となるような箇所のこと。
ちなみに英語だとSingle Point of Failure(SPOF)というらしい。

単一障害点の例
コンポーネント 説明
アプリケーションサーバ アプリケーションサーバが一つしかないと、クリティカルなエラーが発生したときにユーザがシステムを利用できなくなってしまう。よってサーバをレプリケーションしておくことでSPOFにならないようにする必要がある。
ディスクストレージ ディスクストレージが故障するとデータの読み書きができなくなり、システム全体が利用不可になってしまう可能性がある。よってRAIDなどの冗長構成を取る必要がある。
ネットワークスイッチ ネットワークスイッチが故障と、ネットワーク内のサーバ間の疎通ができなくなってしまう。よって冗長なスイッチとネットワーク構成によって、SPOFを解決する必要がある。

トレードオフ
SPOFを解決するためには、レプリケーションや冗長構成などが必要となるので、コストがかかる。
どこまでSPOFの排除に取り組むかはコストとのトレードオフも考えて決定しなければならない。

2017年6月24日土曜日

VagrantのゲストOS間でホスト名参照

 Vagrantfileでホスト名を指定してるのに何故か参照できなかった。

# -*- mode: ruby -*-
# vi: set ft=ruby :

Vagrant.configure("2") do |config|
  config.vm.box = "ubuntu15.04"
  config.ssh.insert_key = false
  config.vm.define "kafka-base" do |server|
    server.vm.network "private_network", ip: "192.168.33.11"
    server.vm.hostname = "kafka-base"
  end
  config.vm.define "kafka-connector" do |server|
    server.vm.network "private_network", ip: "192.168.33.12"
    server.vm.hostname = "kafka-connector"
  end
end

vagrant@kafka-base:~$ hostname
kafka-base
vagrant@kafka-base:~$ ping kafka-connector
ping: unknown host kafka-connector
vagrant@kafka-base:~$ cat /etc/hosts
127.0.0.1 kafka-base  kafka-base
127.0.0.1 localhost
127.0.1.1 vagrant-ubuntu-trusty.vagrantup.com vagrant-ubuntu-trusty
::1     localhost ip6-localhost ip6-loopback
ff02::1 ip6-allnodes
ff02::2 ip6-allrouters

vagrant-hostsというプラグインを入れてみると解決した。
$ vagrant plugin install vagrant-hosts

以下のようにserver.vm.provisionの行を追加すると、ホスト名が設定され、さらにゲストOSの/etc/hostsに仮想マシンのホスト名情報が追記される。
# -*- mode: ruby -*-
# vi: set ft=ruby :

Vagrant.configure("2") do |config|
  config.vm.box = "ubuntu15.04"
  config.ssh.insert_key = false

  config.vm.define "kafka-base" do |server|
    server.vm.network "private_network", ip: "192.168.33.11"
    server.vm.provision :hosts, :sync_hosts => true
  end
  config.vm.define "kafka-connector" do |server|
    server.vm.network "private_network", ip: "192.168.33.12"
    server.vm.provision :hosts, :sync_hosts => true
  end
end

以下のように動作確認してみると、ホスト 名でゲストOS間の通信ができることが分かる。
vagrant@kafka-base:~$ hostname
kafka-base
vagrant@kafka-base:~$ ping kafka-connector
PING kafka-connector (192.168.33.12) 56(84) bytes of data.
64 bytes from kafka-connector (192.168.33.12): icmp_seq=1 ttl=64 time=0.470 ms
64 bytes from kafka-connector (192.168.33.12): icmp_seq=2 ttl=64 time=0.348 ms
^C
--- kafka-connector ping statistics ---
2 packets transmitted, 2 received, 0% packet loss, time 1002ms
rtt min/avg/max/mdev = 0.348/0.409/0.470/0.061 ms
vagrant@kafka-base:~$ cat /etc/hosts
127.0.0.1 localhost
127.0.1.1 kafka-base
192.168.33.11 kafka-base
192.168.33.12 kafka-connector

Vagrantで共通のssh private keyを使う

 Vagrantで複数の仮想マシンを立ち上げて、仮想マシン間でsshの秘密鍵を共有したい場合がある。Vagrant 1.8でのデフォルトの設定ではマシンごとに異なる秘密鍵が生成される。

# -*- mode: ruby -*-
# vi: set ft=ruby :

Vagrant.configure("2") do |config|
  config.vm.box = "ubuntu15.04"
  config.vm.define "kafka-base" do |server|
    server.vm.network "private_network", ip: "192.168.33.11"
  end
  config.vm.define "kafka-connector" do |server|
    server.vm.network "private_network", ip: "192.168.33.12"
  end
end

秘密鍵情報を確認。仮想マシンごとに別の秘密鍵が生成されていることが分かる。
$ vagrant ssh-config
Host kafka-base
  HostName 127.0.0.1
  User vagrant
  Port 2200
  UserKnownHostsFile /dev/null
  StrictHostKeyChecking no
  PasswordAuthentication no
  IdentityFile /Users/kenjih/work/vagrant_ansible_kafka/vagrant/.vagrant/machines/kafka-base/virtualbox/private_key
  IdentitiesOnly yes
  LogLevel FATAL

Host kafka-connector
  HostName 127.0.0.1
  User vagrant
  Port 2201
  UserKnownHostsFile /dev/null
  StrictHostKeyChecking no
  PasswordAuthentication no
  IdentityFile /Users/kenjih/work/vagrant_ansible_kafka/vagrant/.vagrant/machines/kafka-connector/virtualbox/private_key
  IdentitiesOnly yes
  LogLevel FATAL

 しかし、デプロイ自動化を行う場合など、共通の秘密鍵を使えると便利なことが多い。そのような場合は以下のようにconfig.ssh.insert_key = falseという設定を追加すればよい。

# -*- mode: ruby -*-
# vi: set ft=ruby :

Vagrant.configure("2") do |config|
  config.vm.box = "ubuntu15.04"
  config.ssh.insert_key = false
  config.vm.define "kafka-base" do |server|
    server.vm.network "private_network", ip: "192.168.33.11"
  end
  config.vm.define "kafka-connector" do |server|
    server.vm.network "private_network", ip: "192.168.33.12"
  end
end

秘密鍵情報を確認してみると、共通の秘密鍵を利用できることが分かる。
kenjih$ vagrant ssh-config
Host kafka-base
  HostName 127.0.0.1
  User vagrant
  Port 2200
  UserKnownHostsFile /dev/null
  StrictHostKeyChecking no
  PasswordAuthentication no
  IdentityFile /Users/kenjih/.vagrant.d/insecure_private_key
  IdentitiesOnly yes
  LogLevel FATAL

Host kafka-connector
  HostName 127.0.0.1
  User vagrant
  Port 2201
  UserKnownHostsFile /dev/null
  StrictHostKeyChecking no
  PasswordAuthentication no
  IdentityFile /Users/kenjih/.vagrant.d/insecure_private_key
  IdentitiesOnly yes
  LogLevel FATAL

2017年6月11日日曜日

VagrantとAnsibleでKafka環境をつくる(8)

 Vagrant、Ansibleで作ったKafka環境で動作確認をしてみる。
以下の操作はすべてプロジェクトのrootディレクトリから実行するものとします。

まずvagrantで仮想マシンを起動する。
$ cd vagrant
$ vagrant up

続いてansibleでplaybookを適用する。
$ cd ansible
$ ansible-playbook site.yml 

まずはrest proxyと疎通確認を行う。
$ curl 192.168.33.11:8082/topics
["_schemas"]

rest proxy経由でKafkaにデータを送ってみる。
$ curl -X POST -H "Content-Type: application/vnd.kafka.json.v2+json" \
 --data '{"records":[{"value":{"name": "testUser"}}]}' \
      "192.168.33.11:8082/topics/jsontest"
{"offsets":[{"partition":0,"offset":0,"error_code":null,"error":null}],"key_schema_id":null,"value_schema_id":null}

consumerを作成し、先ほど作成したjsontestトピックをサブスクライブする。
$ curl -X POST -H "Content-Type: application/vnd.kafka.v2+json" -H "Accept: application/vnd.kafka.v2+json" \
--data '{"name": "my_consumer_instance", "format": "json", "auto.offset.reset": "earliest"}' \
http://192.168.33.11:8082/consumers/my_json_consumer
{"instance_id":"my_consumer_instance","base_uri":"http://192.168.33.11:8082/consumers/my_json_consumer/instances/my_consumer_instance"}

$ curl -X POST -H "Content-Type: application/vnd.kafka.v2+json" --data '{"topics":["jsontest"]}' \
http://192.168.33.11:8082/consumers/my_json_consumer/instances/my_consumer_instance/subscription

もう1つメッセージを送ってみる。
$ curl -X POST -H "Content-Type: application/vnd.kafka.json.v2+json" \
 --data '{"records":[{"value":{"name": "testUserXXX"}}]}' \
      "192.168.33.11:8082/topics/jsontest"
{"offsets":[{"partition":0,"offset":1,"error_code":null,"error":null}],"key_schema_id":null,"value_schema_id":null}

メッセージをコンシュームする。
$ curl -X GET -H "Accept: application/vnd.kafka.json.v2+json" \       
http://192.168.33.11:8082/consumers/my_json_consumer/instances/my_consumer_instance/records                               
[{"key":null,"value":{"name":"testUser"},"partition":0,"offset":0,"topic":"jsontest"},{"key":null,"value":{"name":"testUserXXX"},"partition":0,"offset":1,"topic":"jsontest"}]

データの送受信を確認できたので、テスト用のコンシューマーを削除する。
$ curl -X DELETE -H "Accept: application/vnd.kafka.v2+json" \
      http://192.168.33.11:8082/consumers/my_json_consumer/instances/my_consumer_instance

VagrantとAnsibleでKafka環境をつくる(7)

 前回マニュアルで試したsystemdからconfluentコンポーネントを起動するための設定をansible化した(成果物)。利用するコンポーネントは以下の4つなので、それぞれのコンポーネント別にroleを作った。

 serviceの設定スクリプトは、Jinja2を使ってtemplatesディレクトリ配下に置いている。taskではtemplatesに置かれたテンプレートを/etc/systemd/system/配下に格納する。設定が変更されると、handlerで指定したようにserviceが起動される。

 以下にzookeeper roleの場合のサンプルを載せておく。

ansible/roles/zookeeper/templates/zookeeper.service.j2
[Unit]
Description=confluent platform zookeeper
After=network.target

[Service]
ExecStart=/usr/bin/zookeeper-server-start /etc/kafka/zookeeper.properties
ExecStop=/usr/bin/zookeeper-server-stop

[Install]
WantedBy=multi-user.target

ansible/roles/zookeeper/tasks/main.yml
- name: zookeeper systemd script
  template:
    src: zookeeper.service.j2
    dest: /etc/systemd/system/zookeeper.service
    owner: root
    group: root
    mode: 644
  notify: start zookeeper

ansible/roles/zookeeper/handlers/main.yml
- name: start zookeeper
  service: name=zookeeper state=started enabled=yes

2017年6月5日月曜日

VagrantとAnsibleでKafka環境をつくる(6)

 zookeeperをサービス登録して、systemdから起動させるようにしてみた。
Ansible化はまだ出来ていないが、とりあえず手動で設定&起動できた。

以下のようなファイルを作っておく。
vagrant@vagrant-ubuntu-trusty:~$ cat /etc/systemd/system/zookeeper.service 
[Unit]
Description=confluent platform zookeeper
After=network.target

[Service]
ExecStart=/usr/bin/zookeeper-server-start /etc/kafka/zookeeper.properties
ExecStop=/usr/bin/zookeeper-server-stop

[Install]
WantedBy=multi-user.target

After=network.targetとすることで、ネットワーク起動後にサービスを開始させるという意味になる。
WantedByのところには、ランレベルを設定する。
multi-user.targetとするとマルチユーザモードで使用されるサービスとなる。

ちなみに、targetの一覧は以下のようにして参照できる。
vagrant@vagrant-ubuntu-trusty:~$ systemctl list-units --type target
UNIT                  LOAD   ACTIVE SUB    DESCRIPTION
basic.target          loaded active active Basic System
cryptsetup.target     loaded active active Encrypted Volumes
getty.target          loaded active active Login Prompts
graphical.target      loaded active active Graphical Interface
local-fs-pre.target   loaded active active Local File Systems (Pre)
local-fs.target       loaded active active Local File Systems
multi-user.target     loaded active active Multi-User System
network-online.target loaded active active Network is Online
network.target        loaded active active Network
nfs-client.target     loaded active active NFS client services
paths.target          loaded active active Paths
remote-fs-pre.target  loaded active active Remote File Systems (Pre)
remote-fs.target      loaded active active Remote File Systems
rpcbind.target        loaded active active RPC Port Mapper
slices.target         loaded active active Slices
sockets.target        loaded active active Sockets
swap.target           loaded active active Swap
sysinit.target        loaded active active System Initialization
time-sync.target      loaded active active System Time Synchronized
timers.target         loaded active active Timers

サービスとして認識しているか確認。
vagrant@vagrant-ubuntu-trusty:~$ sudo systemctl list-unit-files --type=service | grep zookeeper
zookeeper.service                      disabled

サービス有効化。
vagrant@vagrant-ubuntu-trusty:~$  sudo systemctl enable zookeeper
Created symlink from /etc/systemd/system/multi-user.target.wants/zookeeper.service to /etc/systemd/system/zookeeper.service.

サービス起動&確認。
vagrant@vagrant-ubuntu-trusty:~$ sudo systemctl start zookeeper

vagrant@vagrant-ubuntu-trusty:~$ sudo systemctl status zookeeper
● zookeeper.service - confluent platform zookeeper
   Loaded: loaded (/etc/systemd/system/zookeeper.service; enabled; vendor preset: enabled)
   Active: active (running) since Mon 2017-06-05 14:22:49 GMT; 16s ago

デフォルトポートでlistenしているか念のため確認。
vagrant@vagrant-ubuntu-trusty:~$ pgrep -f zookeeper
4542
vagrant@vagrant-ubuntu-trusty:~$ sudo lsof -a -i -p 4542
COMMAND  PID USER   FD   TYPE DEVICE SIZE/OFF NODE NAME
java    4542 root   98u  IPv6  25718      0t0  TCP *:56431 (LISTEN)
java    4542 root  109u  IPv6  25729      0t0  TCP *:2181 (LISTEN)

VagrantとAnsibleでKafka環境をつくる(5)

 前回Javaが入ったので、Kafka環境を入れてみた(成果物)。
KafkaはConfluent Platformを使う。手動でインストールすると以下のようになる。

# install confluent public key
$ wget -qO - http://packages.confluent.io/deb/3.2/archive.key | sudo apt-key add -

# add confluent repository
$ sudo add-apt-repository "deb [arch=amd64] http://packages.confluent.io/deb/3.2 stable main"

# update apt
$ sudo apt-get update 

# install confluent platform
$ sudo apt-get install confluent-platform-2.11

上のインストール作業を行うplaybookは以下のようになる。

[ansible/roles/common/tasks/install_confluent.yml]
- name: install confluent public key
  apt_key: url="http://packages.confluent.io/deb/{{ confluent_repo_version }}/archive.key" state="present"

- name: add confluent repository
  apt_repository: repo="deb [arch=amd64] http://packages.confluent.io/deb/{{ confluent_repo_version }} stable main"

- name: update apt
  apt: update_cache=true

- name: install confluent platform
  apt: "name=confluent-platform-2.11={{ confluent_package_version }} state=present"

{{ XXX }}のところは変数になっている。変数の値は以下のようにvarsディレクトリ内のファイルで定義できる。

[ansible/roles/common/vars/main.yml]
confluent_repo_version: 3.2
confluent_package_version: 3.2.1-1

2017年6月4日日曜日

VagrantとAnsibleでKafka環境をつくる(4)

 Oracle Java1.8を入れるplaybookを書いた(成果物)。

 playbookはroleごとにまとめるのがbest practiceらしい。サーバの役割毎(common, web, dbなど)にroleを設定しているサンプルが多いので、それにならって、common, zookeeper, kafka, schema-registry, rest-proxyというroleをつくろうと思う。

 今回書いたのはJavaのところだけなので、common roleにtaskを書いた。

作成したplaybookのsyntaxチェック。
$ ansible-playbook roles/common/tasks/main.yml --syntax-check

playbook: roles/common/tasks/main.yml

playbookを実行する。
$ ansible-playbook roles/common/tasks/main.yml

PLAY [all] **************************************************************************

TASK [Gathering Facts] **************************************************************
ok: [192.168.33.11]

TASK [Install add-apt-repostory] ****************************************************
changed: [192.168.33.11]

TASK [Add Oracle Java Repository] ***************************************************
changed: [192.168.33.11]

TASK [Accept Java 8 License] ********************************************************
changed: [192.168.33.11]

TASK [Install Oracle Java 8] ********************************************************
changed: [192.168.33.11] => (item=[u'oracle-java8-installer', u'ca-certificates', u'oracle-java8-set-default'])

PLAY RECAP **************************************************************************
192.168.33.11              : ok=5    changed=4    unreachable=0    failed=0

仮想マシンにJava 1.8がインストールされたことを確認。
$ vagrant ssh
vagrant@vagrant-ubuntu-trusty:~$ java -version
java version "1.8.0_131"
Java(TM) SE Runtime Environment (build 1.8.0_131-b11)
Java HotSpot(TM) 64-Bit Server VM (build 25.131-b11, mixed mode)

VagrantとAnsibleでKafka環境をつくる(3)

 Ansibleのplaybookを書こうとしたが、
  • まずはマニュアルで環境を作ってみてうまくいったらplaybookを書きたい
  • マニュアルでいろいろ試行錯誤して環境汚してしまうのは避けたい
ということで何か便利なツールがないか探していたところ、saharaというvagrantのプラグインを見つけた。

saharaを使うと、仮想マシンの環境をサンドボック状態にしてコミット/ロールバックを行うことができる。

以下実行例。

プラグインをインストール。
$ vagrant plugin install sahara
$ vagrant sandbox -h
Usage: vagrant sandbox  []

Available subcommands:
     commit
     off
     on
     rollback
     status

sandboxモードを有効にする。
$ vagrant sandbox on

$ vagrant sandbox status
[default] Sandbox mode is on

sandboxモードの状態で仮想マシンに何かインストールしてみる。
$ vagrant ssh default

vagrant@vagrant-ubuntu-trusty:~$ tmux
The program 'tmux' is currently not installed. You can install it by typing:
sudo apt-get install tmux

vagrant@vagrant-ubuntu-trusty:~$ sudo apt-get install tmux

vagrant@vagrant-ubuntu-trusty:~$ tmux -V
tmux 1.9

ロールバックする。
$ vagrant sandbox rollback

上記のインストールはロールバックされる。
$ vagrant ssh 

vagrant@vagrant-ubuntu-trusty:~$ tmux
The program 'tmux' is currently not installed. You can install it by typing:
sudo apt-get install tmux

VagrantとAnsibleでKafka環境をつくる(2)

Vagrantで作った仮想マシンにAnsibleから接続できるようになった(成果物)。

まず、仮想マシンにsshするときの秘密鍵の場所を調べておく。
kenjih$ vagrant ssh-config
Host default
  HostName 127.0.0.1
  User vagrant
  Port 2222
  UserKnownHostsFile /dev/null
  StrictHostKeyChecking no
  PasswordAuthentication no
  IdentityFile /Users/kenjih/work/vagrant_ansible_kafka/vagrant/.vagrant/machines/default/virtualbox/private_key
  IdentitiesOnly yes
  LogLevel FATAL

ユーザと秘密鍵の場所をオプション指定するとansibleで仮想マシンに接続できる。
kenjih$ ansible -i provisioning/hosts all -m ping -u vagrant --private-key=../vagrant/.vagrant/machines/default/virtualbox/private_key
192.168.33.11 | SUCCESS => {
    "changed": false, 
    "ping": "pong"
} 

が、毎回オプション書くのは面倒なのでconfigファイルを書くといいらしい。 以下のようなファイルをカレントディレクトリに作っておく。
$ cat ansible.cfg
[defaults]
hostfile = provisioning/hosts
remote_user = vagrant
private_key_file = /Users/kenjih/work/vagrant_ansible_kafka/vagrant/.vagrant/machines/default/virtualbox/private_key

すると、オプションなしで接続できる。
$ ansible all -m ping          
192.168.33.11 | SUCCESS => {
    "changed": false, 
    "ping": "pong"
}

接続できたので、ansibleから任意のコマンドを実行してみる。
kenjih$ ansible all -a 'whoami'
192.168.33.11 | SUCCESS | rc=0 >>
vagrant

kenjih$ ansible all -a 'uname -a'
192.168.33.11 | SUCCESS | rc=0 >>
Linux vagrant-ubuntu-trusty 3.19.0-15-generic #15-Ubuntu SMP Thu Apr 16 23:32:37 UTC 2015 x86_64 x86_64 x86_64 GNU/Linux

2017年6月2日金曜日

VagrantとAnsibleでKafka環境をつくる(1)

 まずはVagrantで仮想マシンの作成、起動、停止をするところから。

boxの確認
kenjih$ vagrant box list
centos6     (virtualbox, 0)
ubuntu14.04 (virtualbox, 0)

boxの追加
kenjih$ vagrant box add ubuntu15.04 https://github.com/kraksoft/vagrant-box-ubuntu/releases/download/15.04/ubuntu-15.04-amd64.box

再びBoxの確認(ubuntu15.04が追加されている)
kenjih$ vagrant box list
centos6     (virtualbox, 0)
ubuntu14.04 (virtualbox, 0)
ubuntu15.04 (virtualbox, 0)

初期化
kenjih$ vagrant init ubuntu15.04

仮想マシン起動
kenjih$ vagrant up

仮想マシンへのログイン
kenjih$ vagrant ssh
vagrant@vagrant-ubuntu-trusty:~$
vagrant@vagrant-ubuntu-trusty:~$ uname -a
Linux vagrant-ubuntu-trusty 3.19.0-15-generic #15-Ubuntu SMP Thu Apr 16 23:32:37 UTC 2015 x86_64 x86_64 x86_64 GNU/Linux

仮想マシン状態確認(状態がrunningになっている)
kenjih$ vagrant status
default                   running (virtualbox)

仮想マシン停止
kenjih$ vagrant halt

再び仮想マシン状態確認(状態がpoweroffになっている)
kenjih$ vagrant status
default                   poweroff (virtualbox)

2016年10月1日土曜日

Vagrant + VirtualBox + Ansible

 Ansible簡単で便利なので使った方がいいよーと勧められたので試してみた。

各ソフトウェアの説明
  • Vagrant
    • 仮想環境構築ソフトウェア
    • 設定ファイルを記述することで、仮想環境の構築・設定を自動化できる
  • VirtualBox
    • 仮想化ソフトウェア
    • あるOS上で別のOSを動かすことができる
  • Ansible
    • 構成管理ツール
    • サーバのプロビジョニングを効率化できる

各ソフトウェアのインストール

サンプル
Ubuntuを入れて、nginxをインストールして、nginxを起動するという流れをVagrant + VirtualBox + Ansibleでやってみた。

サンプルは以下のバージョンで動作確認を行った。
  • Vagrant 1.8.6
  • VirtualBox 5.1.6
  • Ansible 2.0.2.0
Ubuntu 14.04のboxを追加
$ vagrant box add ubuntu14.04 \
https://cloud-images.ubuntu.com/vagrant/trusty/current/trusty-server-cloudimg-amd64-vagrant-disk1.box
$ vagrant box list
ubuntu14.04 (virtualbox, 0)

Vagrantfileのテンプレート作成
適当な作業ディレクトリを作成してcdする。
vagrant initすると、Vagrantfileが自動生成される。
$ mkdir ansible_sample
$ cd ansible_sample
$ vagrant init

Vagrantfileの編集
テンプレートを編集して以下を記述する。
config.vm.box = "ubuntu14.04"
config.vm.network "private_network", ip: "192.168.33.10"

config.vm.provision "ansible" do |ansible|
  ansible.playbook = "provisioning/playbook.yml"
  ansible.inventory_path = "provisioning/hosts"
  ansible.limit = 'sample'
end

inventory fileの編集
inventory fileはAnsibleの管理対象を定義するファイル。
今回の場合はUbuntuのVMなのでそのIPアドレスを書いておく。
[sample]のところは好きな名前でよい。
$ mkdir provisioning
$ emacs provisioning/hosts
[sample]
192.168.33.10

playbook作成
hostsにはinventory fileで定義した名前を書く。
become: yesはsudo実行の意味。
$ emacs provisioning/playbook.yml
---
- hosts: sample
  become: yes
  user: vagrant 
  tasks:      
    - name: install nginx
      apt: name=nginx update_cache=yes
    - name: restart nginx
      service: name=nginx state=restarted

実行
実行前にディレクトリ構造が以下のようになっていることを確認。
$ tree
.
├── Vagrantfile
└── provisioning
    ├── hosts
    └── playbook.yml

問題なければ、VMを起動&プロビジョン実施。
$ vagrant up
$ vagrant provision

確認
ゲストOSにsshしてservice statusを調べる。
$ vagrant ssh
vagrant@vagrant-ubuntu-trusty-64:~$ service nginx status
 * nginx is running

ホストOSからcurlしてみる。
$ curl 192.168.33.10 
Welcome to nginx!の文字が表示されればOK。

2016年1月10日日曜日

Dockerメモ

 Dockerの勉強をした。オフィシャルサイトのどこを見ると何が載っているかをメモしておく。

Macにdockerをインストール

コンテナの実行(インタラクティブコンテナ)
コンテナの実行(デーモナイズドコンテナ)

Python Flaskアプリケーションの実行
port binding(自動設定、port番号指定)
コンテナで動作するアプリケーションのログ確認
コンテナで動いているプロセスの確認
コンテナの停止
コンテナの再起動
コンテナの削除

ローカルのhostにあるdocker imageの確認
docker imageの取得
docker imageの検索
docker imageの作成
Dockerfileを使ったimageの作成
既存imageへのタグ設定
Docker Hubにimageをpush
docker imageの削除

コンテナに名前をつける
ネットワークの作成
ネットワークを指定してコンテナを起動
起動中のコンテナのシェルを開く
同一ネットワークで動作するコンテナへの接続

Data volumeの追加
ホストディレクトリをdata volumeとしてマウント
OS X, windowsでDocker Machineを使っている場合のマウント方法
Data Volume Containerを使ったコンテナ間のデータ共有
Data volumeを使ったバックアップ、リストア、マイグレイーション

Dockerコマンドを使ったDocker Hubへのアクセス
Automated BuildsによるGitHubとのsync