Docker: Composeで複数コンテナを協調動作させる

 Dockerコンテナも適度に機能を分割させてコンテナを用意すべきだろう。たとえばアプリのスクリプトを走らせているコンテナとDBコンテナを分けるとか。で、分けるときにはDockerに用意されたComposeが役に立つ。

 わけたときにComposeを使ってとりあえずできること
・そのコンテナ間で有効なホスト名をつけて相互にアクセス設定できる
・管理する複数コンテナを一括で走らせたり止めたり

 つい先日、Webアプリを作ったが機能的な観点から構成を三つのコンテナに分けた。一つはPythonスクリプトを走らせるWebアプリのメイン機能コンテナ、二つ目はそのアプリのDBコンテナ、三つめはDBコンテナをのぞけるようにphpmyadminコンテナである。
 まずざっくりとcomposeスクリプトから。このスクリプトを使うことで、コンテナの動作管理を一括でできるようになる。コンテナ間のホスト名アクセスもここで設定できる。その例が↓。
sqlinj_db:

image: mysql
ports:
- "3306:3306"
environment:
MYSQL_USER: "foo"
MYSQL_PASSWORD: "bar"
MYSQL_ALLOW_EMPTY_PASSWORD: "yes"
sqlinj_app:
build: ./sqlinjection
ports:
- "8686:80"
links:
- sqlinj_db:db
myadmin:
image: phpmyadmin/phpmyadmin
ports:
- "8687:80"
environment:
PMA_HOST: "db"
links:
- sqlinj_db:db

 コンテナは当然、自分でDockerfileを書いたものから、イメージをpullしてすぐ走らせたいものまでいろいろ用意できる。
 今回は三つコンテナを用意しており、Dockerfileを書いているのはWebアプリのメインコンテナだけ。sqlinj_appというコンテナである。buildキーに続く値で、ビルドを実行するディレクトリを指定している。同様に、portsでコンテナとホストのポートバインディング、linksでコンテナ間のホストアクセス設定を行っている。コンテナ間でホスト名アクセスを行いたい場合、アクセスを受ける側ではなく、リクエストを送る側のlinksで設定を行う。linksの値は[name1]:[name2]という形で書かれている。name1がcomposeでつけているコンテナの名前、name2が設定したいホスト名である。例示したcomposeスクリプトサンプルでは、sqlinj_appコンテナ内からsqlinj_dbコンテナにアクセスしたければdbというホスト名でアクセスできるようになっている。
 あとの二つのコンテナはデフォのものに環境変数を渡して設定しているだけなのでよしなに。

 DBサーバは環境変数を与える以外にはカスタムしたくなかった、めんどうだから。じゃあDBの初期化どうするの?となれば、Webアプリのメインコンテナが起動するとき、DBの初期化コマンドを仕込んでおくようにする。
 Composeで管理されるコンテナに起動命令はできるが、DBコンテナの中のMySQLの起動を待つようなオプションコマンドはない。だから他コンテナから普通にDB接続しようとすると失敗するだろう。DBコンテナ外では、MySQLの起動を待つシェルスクリプトを書いて、それで待つのが一般的なようだ。
http://qiita.com/ry0f/items/6e29fa9f689b97058085

 composeスクリプトと各コンテナが用意できたら、あとはdocker-composeコマンドでコンテナが容易にコントロールできる。

ビルド
docker-compose build


デプロイ
docker-compose up -d


停止
docker-compose stop


削除
docker-compose remove

comment: 0

ITというものの捉え方の更新を怠っていた

 会社で打ち合わせをやるとなると、たいてい上司が「資料を印刷して持ってきてくれ」と言う。それがたとえ一行のテキストだとしても。一行のテキストだとしても。一行。まがりなりにもIT企業なのにどうなってるのさ、いつになったらそこから脱却できるのさ、と思いつつも、「紙は見やすい。ノートPCやタブレットは見づらい」とか言われるともはやあきらめるしかない。一行なのに。
 そんなでもどうにかIT化で紙から電子に変えなきゃいかんなーって思っていた。そしたら日経の素晴らしい記事にどつかれた。
デジタル化は企業文化変革 負け犬にならないために
ドコモの執行役員の人が書いたそうで、それならこんなちゃんと時勢をつかんだものになるなーと感じた。

"日本企業の多くの従業員の理解は「紙の会議資料がなくなって決裁処理も電子化だな」とか「部門別管理会計では満足せずプロダクト別管理会計も導入するのかな」といったレベルだろう"
スミマセン…

"消費者と企業の接点は、店頭やマスメディアから離れ、スマートフォン上の人気サービスに移ろうとしている。消費者がどのように商品と企業ブランドを認知し、関心を持ち、購入に至るかの行程が変化している"

"米ドミノ・ピザは15年にデジタルにかじを切り、本社ビルに勤務する従業員700人のうち、300人がエンジニアとなった。注文方法充実化や発注データ解析による営業効率化を推進、売り上げはライバル企業を上回っている"

"ここ最近でGEが学んだことがある。それは、20年前に多くの産業界の企業が行い、現在も続いているIT業務のアウトソーシングは、今日においては負け犬の戦略であるということだ"

 個人的にはドミノピザ本社の300/700人がエンジニアになったというのがビックリなのだが、そういえばゴールドマンサックスあたりでも似たようなことになっていると聞いた。もう、どうやって業務をITで効率化できるかってのを人を集めて開発とは別の場所で考えている時代ではなく、大量データをITドリヴンで処理して、そこから経営判断を行っていくとかって時代になっていた。そういう時代が来てるとかじゃなくてもうなっている。DevOpsとかの事例ってこういうところから来てるんだろうな。

 ぼくが高専に通っていたころ、インターネットというのが一般化した。パソコンを持っている家ではそれを使っていくらかのことができた。うちにもパソコンはあったので、ヤフオクで自分のものや友達に頼まれたものをやり取りしていた。そのころはまだ、パソコンの前に座るという手間があった。
 今はガラケーを経てスマフォ、タブレットの時代になった。もはやパソコンの前に座る必要がなく、多くの人がいつでもどこでもインターネットを使える端末を携帯している状態になった。家に帰ってからしかできなかったヤフオクがいつでもできるようになった。それだけではなくSNSも浸透した。サービスも広告もそのプラットフォームを無視できないどころか、そこを第一ターゲットに考えるべき状況になっていた。ITは消費者の家にあった時代から、もう消費者個々の手元にある。ITを駆使できれば、多くの消費者に直接リーチできる、すぐに。

 いま、サービスを考える業種というのは面白そうな気がしてきた。もう10年前よりずっと多くの人をターゲットにできるようになっている。開発側も多くの人へより洗練されたサービスを届けようと、改良の速度を高めてイテレーションする手法の事例がどんどん出てきている。うまくクラウドやツールを使うことでどんどん開発手法が加速している。そう考えると、すでにもう息切れして止まっているのはやばい。神エクセルよさようなら。
comment: 0

ConoHaのVPSにDebian9を入れる

 Debian9がリリースされたのでサーバOSにしようとConoHaのVPSに入れてみた。その過程。

1.VPSを適当に立てる
 管理コンソールへいき、適当なスペック、適当なOSイメージでVPSを立てる。立てたらそのVPSの管理画面で電源を落とす。

2. 必要情報を取得
 ConoHaのAPI画面に移動し、ユーザを追加する。テナント名、ユーザ名、パスワードをメモ。

3..CLIツールを使ってISOをVPS上に用意する
 WindowsでやったのでまずCLIツールのZIPをダウンロード、
https://github.com/hironobu-s/conoha-vps
 ZIPを解凍したらEXEが一つ入っていたので、そのディレクトリでPowerShellを開いて以降のコマンドを実行した。

 続いてVPS上にISOを落とす。
./conoha-iso download -i https://cdimage.debian.org/debian-cd/current/amd64/iso-cd/debian-9.0.0-amd64-netinst.iso -u [APIユーザ名] -p [APIパスワード] -n [テナント名] -r [リージョン]

 そして次のコマンドでISOの準備が完了したことを確認できるまで適度に繰り返して待つ。
./conoha-iso list  -u [APIユーザ名] -p [APIパスワード] -n [テナント名] -r [リージョン]


4.ISOイメージ挿入
./conoha-iso insert -u [APIユーザ名] -p [APIパスワード] -n [テナント名] -r [リージョン]


5.インストール
 ISOイメージが挿入された状態でVPSを起動。コンソールを開くと、インストール開始画面が表示される。好きなインストール方法を選ぶ。ちなみにグラフィックでやるのはマウスが効かないので向いていないが、タブキーをうまく利用すればできる。チェックボックスの切り替えはスペースキーで。

6.インストールが終わったらディスクを抜く
 インストールが終わったら、一度VPSの電源を落として停止状態になるのを待つ。停止状態になったらイジェクト。
./conoha-iso eject -u [APIユーザ名] -p [APIパスワード] -n [テナント名] -r [リージョン]


7.起動確認
 またVPSの電源を入れてコンソールを開いて起動確認。
comment: 0

遠隔でMongoDBサーバのバックアップを取る2

 前回に構築したMongoDBサーバの自動遠隔バックアップシステムを削除し、新しくバックアップシステムを組んだ。今回はMongoDBサーバでバックアップコマンドを実行し、それをAzure Blob StorageにPythonでアップするという流れ。

backup.sh

#!/bin/sh
cd /home/h/backup
mongodump --host foo -u bar -p boo
tar zcvf dump.tar.gz dump
python3.5 /home/h/up.py
rm -rf *


up.py

from azure.storage.blob import BlockBlobService
import datetime

account = "xxx"
key = "yyy"
block_blob_service = BlockBlobService(account_name=account, account_key=key)
filename = datetime.datetime.now().strftime("%Y%m%d")
block_blob_service.create_blob_from_path("mongo", filename, "dump.tar.gz")



comment: 0

遠隔でMongoDBサーバのバックアップを取る1

 クッソなバックアップシステムを組んでしまった。まあとりあえず動く。だからメモとして残すが、バックアップシステムは組みなおす。



 MongoDBのホスティングサービスを使いたいのだが、経済的な理由から安いVPSをMongoDBサーバにしている。
ConoHaにMongoDBサーバを立てた

 ↑の自動バックアップを組みたい。バックアップは外部に置く。外部にバックアップを置くことを考えると、もっとも簡単な方法は、バックアップを置く端末からバックアップコマンドを実行することだろう。
mongodump --host foo -u bar -p pw


 うちの常時稼動RaspberryPiで上記を実行したい。しかしそのコマンドが入ったMongoDB ToolsはARMでは64bit用しか用意されていない。標準のRaspbianは今のところ32bitOSなので今のところ無理。経済的に超ローコストで問題を解決したい。
 RaspberryPiにMongoDB Toolsは入れられん。だけどAzureのCLIは入れられる…
・RaspberryPiでAzureのVMの電源を入れたり切ったり
→AzureのVMにMongoDB Toolsを入れてそっちでバックアップ
 上記のようにすれば、VMの電源は一時的にしか入らないので大したコストはかからん。

 まずRaspberryPiにAzureCLIを入れて、VMの電源をコントロールできるようにする。AzureCLIをインストールしたら、下記のような.shを用意してCRONで走らせるようにする。
az login -u foo -p bar

az account set -s xxx-xxx-xxx
az vm start -g xxx -n yyy
#az vm deallocate -g xxx -n yyy


 次にVMでmongodumpコマンドをCRONに入れる。これでMongoDBサーバのバックアップが自動でとれるようになった。しかもVMは一時的にしか電源が入らないからコストにはならん…アホらし。
 MongoDBサーバのバックアップを取るのに、コストを抑えるためだからってわざわざこんな構成組むのはアホらし。
・問題解決はシンプルに
・金を払ってシンプルに解決できるならそれで
・金がなくても極力シンプルに


 課題はシンプルに解決する。一通り組み終わって、べつの解決法を思いついたのでバックアップシステムの組み直し。
comment: 0