Deisのpostgresをoff-clusterにする(Cloud SQLを利用)

やること

postgresをoff-clusterする。 で、そのpostgresをどこに立てるかというとGCEにたてるかGCPのmangaedなCloud SQL(RDSみたいなやつ)があるので、どっちにするかということで、今回はCloud SQLを使ってみた。

Cloud SQL PostgreSQL beta

Cloud SQLのポスグレはまだbeta版。なので、terraformにも来てない。けど、GCPは全体的に、公式docにGUIでconsoleでやるか、CLIでやるかっていうのが並列で揃ってて、とても親切。AWSみたいに、AWS Consoleで突然何かが色々できてしまうってことがない感じ。

f:id:masato47744:20170422013302p:plain

作成は、rakeタスクにまとめるとこんな感じ。簡単

namespace :gcp do
  task :create_postgresql do
    sh %Q(gcloud beta sql instances create deis-cloudsql-postgres \
          --database-version=POSTGRES_9_6 \
          --activation-policy=ALWAYS \
          --backup-start-time=16:00 \
          --gce-zone=asia-northeast1-a \
          --maintenance-window-day=SUN \
          --maintenance-window-hour=17 \
          --tier=db-n1-standard-1 \
          --storage-type=SSD \
          --storage-size=10GB \
          --storage-auto-increase \
          --region=asia-northeast1
          )
  end
end

deis君からCloud SQLに接続するには

Cloud SQLに接続するには、何通りか方法があるけど、基本的にcloud sql proxyというのをたてて、それ経由でアクセスするっていうのがいい方法のようだ。 関係ないけど、Kubernetsとかにも言えるけどこういうのうまいなって思う。

cloud sql proxyを起動したマシン上で、localhostに対してDB接続しにいくと、つながるようになってる。

で、GKEの場合どうするかっていうと、sidecarパターンというやり方で、同一Pod内にcloud sql proxyのdocker image(imageが用意されてるところも憎い!)を起動させてそれをmountしてlocalhostをproxyとして接続できるようになる。うまい。

ただ、Deis君の場合は既にpodは固定されていて、ちょっと個別にpodを書き換えたりするのは面倒・・・っていうかやり方分からない。forkして、自分で追加したりしないといけないのかもしれない。なので、cloud sql proxyのパターンは使えない。もしかしたら、clusterたてるときに各nodeに初期処理入れてcloud sql proxyのinstallとかできるのかな。。

Cloud SQLは外部からアクセスする際に、IPアドレスを指定しておけば、そこからのアクセスは受け付けるようになる。なので、今回は、GKEのnodeのIPアドレスを指定してあげたら接続できた。 AWSだとNAT Gatewayがいたりするんだけど、GCPの場合はそういうのなさそう?やるなら、自分でNAT instance立てろ的な感じかもしれない。

nodeのIPアドレスたちは、kubectlコマンド使ってとれるようになってる。便利。この情報は、kubectl Cheat Sheetに書いてあった。

kubectl get nodes -o jsonpath='{.items[*].status.addresses[?(@.type=="ExternalIP")].address}'

deis用のユーザーとdatabaseの作成

GCPは、cloud shellっていうコンソールからssh接続できる風なやつが用意されてて、それ経由で作成してもOK。(AWSにも欲しい・・)

f:id:masato47744:20170422013525p:plain

ただ、これもCLIが用意されてるのでそっちのがいい。ので、そうした。

  task :create_database do
    sh %Q(gcloud beta sql users set-password postgres no-host \
          --instance=deis-cloudsql-postgres --password=#{ENV["POSTGRES_PASSWORD"]}
          )
    sh %Q(gcloud beta sql users create deis no-host \
          --instance=deis-cloudsql-postgres --password=#{ENV["POSTGRES_DEIS_PASSWORD"]}
          )
    sh %Q(gcloud beta sql databases create deis \
          --instance=deis-cloudsql-postgres
          )
  end

off-clusterにしてhelm install

さっき作ったdbの情報をvalues.yamlに書く。

cloud sqlIPアドレスは、gcloudコマンドでとれる。結果はYAML形式でかえってくるので、rubyだといい感じに処理できる。それを--set database.postgres.hostで渡してあげればOK。passwordとかも、環境変数に入れておいてinstallをする。

namespace :helm do
  task :install do
    sh %Q(helm install deis/workflow --namespace deis -f values.yml \
          --set gcs.key_json="$(cat gcloud-service-key.json | base64)" \
          --set database.postgres.password=#{ENV["POSTGRES_DEIS_PASSWORD"]} \
          --set database.postgres.host=#{sql_instance_address}
        )
  end
  
  def sql_instance_address
    res = `gcloud sql instances describe deis-cloudsql-postgres`
    YAML.load(res)["ipAddresses"].first["ipAddress"]
  end
end

動いているようだ

$ kd get pods
NAME                                     READY     STATUS    RESTARTS   AGE
deis-builder-1364651073-83r7x            1/1       Running   0          43m
deis-controller-2711454920-g32nn         1/1       Running   0          43m
deis-logger-176328999-06nwq              1/1       Running   2          43m
deis-logger-fluentd-fbg4m                1/1       Running   0          43m
deis-logger-fluentd-nt0tq                1/1       Running   0          43m
deis-logger-fluentd-ttlwl                1/1       Running   0          43m
deis-logger-fluentd-zc6hd                1/1       Running   0          43m
deis-logger-redis-304849759-njc4w        1/1       Running   0          43m
deis-monitor-grafana-432627134-b12zt     1/1       Running   0          43m
deis-monitor-influxdb-2729788615-6pl28   1/1       Running   0          43m
deis-monitor-telegraf-5rhmv              1/1       Running   1          43m
deis-monitor-telegraf-ckfvc              1/1       Running   1          43m
deis-monitor-telegraf-pdhj8              1/1       Running   1          43m
deis-monitor-telegraf-q0d2h              1/1       Running   1          43m
deis-nsqd-3597503299-sxcss               1/1       Running   0          43m
deis-registry-169338602-4hzmk            1/1       Running   0          43m
deis-registry-proxy-7h5f2                1/1       Running   0          43m
deis-registry-proxy-k8vv4                1/1       Running   0          43m
deis-registry-proxy-np9ks                1/1       Running   0          43m
deis-registry-proxy-xcsx8                1/1       Running   0          43m
deis-router-2126433040-7js0d             1/1       Running   0          43m
deis-workflow-manager-2528409207-55vjg   1/1       Running   0          43m

うまくいってないと、STATUSがCrashになってたり、RESTARTSが増え続ける。 ちなみに、kdkubectl --namespace=deisのalias。Tipsが公式に書いてあた

追記:これで解決

mpon.hatenablog.com