Edited at

Azure Web App for Containers 上で kong (API gateway) を docker で動かす


はじめに

image.png


この記事で説明する/しないこと



  • kong 自体の説明は割愛したい。API Gateway のソフトウェア。


    • Hosted なサービスである、Mashape というサービスが、 そのプラットフォームである Kong をオープンソース化した。

    • kong の代替はこのあたりApigeeTykKrakenD あたりとのこと。



  • なぜ API Gateway か、についても割愛したい。すでに多くは API Gateway Pattern などで言及されている。

  • 大事:kong は client から接続用と admin から接続用で二つポートが必要なのだが、Azure Web App for Containers はポートを一つしか公開できない制約があるため、Web App をそれぞれようにデプロイする。以下のような具合。


    1. client 接続用 kong.azurewebsite.net -> 8000 port

    2. admin 接続用 kong-admin.azurewebsite.net -> 8001 port




なぜ


  • Web App for Containers 上に API Gateway を置くことで、API アプリケーションを複数または単体で公開するときに Gateway レイヤを設けることができる。

  • Azure の App Service プランの性質上、複数アプリケーションを一つのプラン内で作成できるので、(端的に言うと、価格は1インスタンス分で複数アプリケーション)トラフィックの成長に合わせて少ないうちは節約できる。

  • なぜ kong を選んだか、についてはいくつか理由はあるが、ひとつ挙げると、nginx 上に OpenResty で実装されていて、軽量そうなところが個人的に好みである、という点。Gateway Layer に重厚なものは避けたい。


    • KrakenD というのは今回知ったが、もっとgolang 製でさらに軽量らしい。試してみたい。



  • 必要なもの全て Cloud 上の PaaS 環境を使って構築したい。


環境

$ docker version

Client:
Version: 17.12.1-ce
API version: 1.35
Go version: go1.9.4
Git commit: 7390fc6
Built: Tue Feb 27 22:17:40 2018
OS/Arch: linux/amd64

Server:
Engine:
Version: 17.12.0-ce
API version: 1.35 (minimum version 1.12)
Go version: go1.9.2
Git commit: c97c6d6
Built: Wed Dec 27 20:12:29 2017
OS/Arch: linux/amd64
Experimental: true


手順

原則、Kong 公式の手順通りだが、デプロイ先を local docker コンテナではなく、Azure Web App for Containers と Azure Database for PostgreSQL としている。

https://getkong.org/install/docker/


まずは、Local kong -> Azure PostgreSQL


Azure Database for PostgreSQL

Azure PostgreSQL から作る。Azure ポータルからポチポチ作った。

次にローカル環境から接続するので、ここでメニュー「接続のセキュリティ」から「自分の IP を追加」しておく。

さらに、同じメニュー内で 「SSL 設定」の 「SSL 接続を強制する」を "無効" にしておく。

この設定は本来は非推奨。今回、最終的に接続は Azure 内(Web App -> PostgreSQL)に閉じるのでまだいいが。

TODO: ちゃんと SSL 接続する手順は後ほど追記したい。

image.png

接続の確認は楽をしたいので GUI で済ませたい。ローカルの docker コンテナに、 pgadmin4 を起動して確認した。

https://hub.docker.com/r/dpage/pgadmin4/

手順は、Docker Hub 上記ページに詳細はあるが、ざっくりと以下の具合。

docker pull dpage/pgadmin4

docker run -p 8080:80 \
-e "PGADMIN_DEFAULT_EMAIL=container@pgadmin.org" \
-e "PGADMIN_DEFAULT_PASSWORD=Conta1ner" \
-d dpage/pgadmin4

Web UI http://localhost:8080 のログインはデフォルト以下で。

Default: container@pgadmin.org

Default: Conta1ner


Azure 上 PostgreSQL に初期データを投入する

pgadmin4 上で kong という database を作成する。

:exclamation: 注意:オリジナルの手順ではこのステップがない。PostgreSQL は docker コンテナ上で起動していて、kong Database は既に作成済みなため。

kong migrations bootstrap コマンドを実行する

$ docker run --rm \

-e "KONG_DATABASE=postgres" \
-e "KONG_PG_HOST=****.postgres.database.azure.com" \
-e "KONG_PG_USER=****" \
-e "KONG_PG_PASSWORD=****" \
kong:latest kong migrations bootstrap --vv

**** 部分はそれぞれの環境に応じて置き換えて。--vv を付けると debug モードでやってくれる

上記の接続元 IP 設定や、SSL設定が漏れていると、ここで接続エラーになってしまうはず。


local docker container 上に kong アプリケーションを起動する

docker run (**** 部分はそれぞれの環境に応じて置き換えて。)

docker run -d --name kong \

-e "KONG_DATABASE=postgres" \
-e "KONG_PROXY_ACCESS_LOG=/dev/stdout" \
-e "KONG_ADMIN_ACCESS_LOG=/dev/stdout" \
-e "KONG_PROXY_ERROR_LOG=/dev/stderr" \
-e "KONG_ADMIN_ERROR_LOG=/dev/stderr" \
-e "KONG_ADMIN_LISTEN=0.0.0.0:8001" \
-e "KONG_ADMIN_LISTEN_SSL=0.0.0.0:8444" \
-e "KONG_PG_HOST=****.postgres.database.azure.com" \
-e "KONG_PG_USER=****" \
-e "KONG_PG_PASSWORD=****" \
-p 8000:8000 \
-p 8443:8443 \
-p 8001:8001 \
-p 8444:8444 \
kong:latest

確認する。 8001 ポートは admin API のほう。

curl -i http://localhost:8001 


Azure Web App に kong をデプロイする

さあ、これで最後。大事なことをもう一回。



  • 大事:kong は client から接続用と admin から接続用で二つポートが必要なのだが、Azure Web App for Containers はポートを一つしか公開できない制約があるため、Web App をそれぞれようにデプロイする。以下のような具合。


    1. client 接続用 kong.azurewebsite.net -> 8000 port

    2. admin 接続用 kong-admin.azurewebsite.net -> 8001 port




Web App for Containers は 二つ 作成する。Azure Portal から Docker Hub の "kong:latest" イメージで作成する。

上記 docker run -e "HOGEHOGE=hogehoge" で指定した環境変数は、Azure Web App ではアプリケーション設定として設定する。

Azure Portal 上から設定も可能だが CLI が楽できる。

参考:Azure CLI: az webapp config appsettings set

Kong の設定、 /etc/kong/kong.conf の内容は、実行環境の環境変数によって上書きすることができる。


参考:どんな設定ができるか。 Kong Configuration Reference

Environment variables

All environment variables prefixed with KONG_



1. Client 接続用

Web App が作成されたら、環境変数を設定する。

Web App の公開ポートは WEBSITES_PORT で設定可能。

export RG=****(作成したリソースグループ)****

export APPNAME=****(作成したApp名)****
az webapp config appsettings set -g $RG -n $APPNAME --settings \
KONG_DATABASE=postgres \
KONG_PROXY_ACCESS_LOG=/dev/stdout \
KONG_ADMIN_ACCESS_LOG=/dev/stdout \
KONG_PROXY_ERROR_LOG=/dev/stderr \
KONG_ADMIN_ERROR_LOG=/dev/stderr \
KONG_ADMIN_LISTEN=0.0.0.0:8001 \
KONG_ADMIN_LISTEN_SSL=0.0.0.0:8444 \
KONG_PG_HOST=****.postgres.database.azure.com \
KONG_PG_USER=**** \
KONG_PG_PASSWORD=**** \
WEBSITES_PORT=8000

アクセスしてみる。URL はそれぞれの環境に応じて。ここでは hello-kong としている。ここでポートを 8000 と付ける必要はない。80 で公開されている。

curl -i https://hello-kong.azurewebsites.net

ちゃんど起動しているか、こんな CLI コマンドでログを tail できる。

az webapp log tail -g $RG -n $APPNAME 

以下のようなメッセージが表示されたらOK。hello-kong の部分は アプリケーション名がくる。

2018-03-16 HH:MM:SS.SSS INFO  - Container hello-kong_0 for site hello-kong initialized successfully.


2. Admin 接続用

export RG=****(作成したリソースグループ)****

export APPNAME=****(作成したApp名 admin 用)****
az webapp config appsettings set -g $RG -n $APPNAME --settings \
KONG_DATABASE=postgres; \
KONG_PROXY_ACCESS_LOG=/dev/stdout; \
KONG_ADMIN_ACCESS_LOG=/dev/stdout; \
KONG_PROXY_ERROR_LOG=/dev/stderr; \
KONG_ADMIN_ERROR_LOG=/dev/stderr; \
KONG_ADMIN_LISTEN=0.0.0.0:8001; \
KONG_ADMIN_LISTEN_SSL=0.0.0.0:8444; \
KONG_PG_HOST=****.postgres.database.azure.com; \
KONG_PG_USER=****; \
KONG_PG_PASSWORD=****; \
WEBSITES_PORT=8001

アクセスしてみる。URL はそれぞれの環境に応じて。ここでは hello-kong-admin としている。ここでポートを 8001 と付ける必要はない。80 で公開されている。

curl -i https://hello-kong-admin.azurewebsites.net

ちゃんど起動しているか、こんな CLI コマンドでログを tail できる。

az webapp log tail -g $RG -n $APPNAME 

以下のようなメッセージが表示されたらOK。hello-kong の部分は アプリケーション名がくる。

2018-03-16 HH:MM:SS.SSS INFO  - Container hello-kong-admin_0 for site hello-kong-admin initialized successfully.


参考 URL


やり残し


  • 全体の構成図を追記する

  • SSL 接続の手順を追記する