0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

Kong GatewayのカスタムエンティティをKubernetes上で利用する

Last updated at Posted at 2025-01-07

前回「Kong Gatewayのカスタムエンティティを作成する」という記事でPongo(Docker)を使ってカスタムエンティティの作成から動作確認まで行った。
これをKubernetes上で動かすためのメモ。
既存のドキュメントだとカスタムプラグインをKICで動かす方法については記載があるが、DAOを含む場合については記載がないので参考になれば幸いである。

なお、「Kong Gatewayのカスタムエンティティを作成する」の延長で書いているため、前の記事を読んでいることが前提となる。

カスタムプラグインのおさらい

DAOを含むカスタムプラグインの構造は以下となる。

complete-plugin
├── daos.lua
├── handler.lua
├── migrations
│   ├── init.lua
│   └── 000_base_complete_plugin.lua
└── schema.lua

schema.luahadnler.luaがカスタムプラグインの実装にあたり、カスタムエンティティの実装はdaos.luaで行い、DBの初期化はmigrations以下のコードで行う。
migrations以下のファイルは以下のようになる。

init.lua:DBの初期化で利用するファイルの定義
000_xxx.lua:実際に初期化で使うコード

ポイントとしてはmigrationsのディレクトリはどうも必須っぽく、ディレクトリなしでフラットにファイルを配置してもinit.luaや000_xxx.luaは読み込まれずにテーブルの初期化が出来ない。
Kubernetesにおいて少し面倒なのが、ConfigMapではディレクトリ構造は表現できない点である。
そのため、カスタムプラグインをConfigMapで登録する場合はConfigMapとは別にディレクトリ構造を用意してあげる必要がある。

カスタムプラグインの構築

ここでは前回記事で作成したファイルを以下のように配置したところからスタートする。

$ tree ./dao-test
./dao-test
├── daos.lua
├── handler.lua
├── migrations
│   ├── 000_base_my_plugin.lua
│   ├── 001_100_to_110.lua
│   └── init.lua
└── schema.lua

前回記事で作成した際にプラグイン名はmypluginとしていたが、ここではdao-testに変更している(schema.lua内も変更済み)。

最初にConfigMapを作成してカスタムプラグインをKubernetesクラスタ上にロードする。migrationsディレクトリ以下も登録するよう--from-fileを各ディレクトリに対して指定する。

kubectl create cm kong-plugin-dao-test --from-file=./dao-test/ --from-file=./dao-test/migrations  -n kong --dry-run=client -o yaml | kubectl apply -f -

後述するが、migrations以下はカスタムプラグイン本体とは別でマウントするため、ConfigMapをルートディレクトリとmigrationsで分けてもいいと思う(ここでは面倒だったので1つにまとめた)。

次にカスタムプラグインのためにHelmのvalues.yamlを編集する。
ここではvalues.yamlの詳細は触れず、変更が必要な箇所のみ記載する。
また、大前提としてTraditionalモードでデプロイするものとし、Hybridモードではデプロイしない
Hybridモードの場合、Data PlaneからDAO経由でのDB更新処理が出来ないためである。

カスタムプラグインの追加箇所は以下となる。

env:
  plugins: bundled,dao-test
plugins:
  configMaps:
  - name: kong-plugin-dao-test
    pluginName: dao-test

上記の部分はDAOの利用がなくても同じである。
次にDBのテーブルの初期化のためのmigrationsを利用するために以下を追加する。

deployment:
  enabled: true
  userDefinedVolumes:
  - name: kong-plugin-dao-test-migration
    configMap:
      name: kong-plugin-dao-test
  userDefinedVolumeMounts:
  - name: kong-plugin-dao-test-migration
    mountPath: /opt/kong/plugins/dao-test/migrations

UserDefinedVolumesUserDefinedVolumeMountsはPod内にディレクトリを作ってConfigMapをマウントするためのKongのHelmChartのパラメータである。

上記の内容を含むHelmのvalues.yamlを使ってKong Gatewayをデプロイする。
デプロイ後、Podの中を見てみると先ほどの設定によって以下のような感じでPod内からプラグインが見えるようになる。

$ kubectl exec -it kong-aws-cp-kong-bd856c4d8-m64l8 -c proxy -- ls -R /opt/kong/plugins
/opt/kong/plugins:
dao-test

/opt/kong/plugins/dao-test:
000_base_my_plugin.lua	daos.lua     init.lua	 schema.lua
001_100_to_110.lua	handler.lua  migrations

/opt/kong/plugins/dao-test/migrations:
000_base_my_plugin.lua	daos.lua     init.lua
001_100_to_110.lua	handler.lua  schema.lua

動作確認

追加したカスタムプラグインはリクエストのヘッダに"mykey-add:<文字列>"を含んでいると文字列部分をDB上のテーブルに格納する。
そのためプラグイン設定後に通信を行い、その前後のテーブルの状態を確認することで上手く設定できているかどうかを確認する。

最初にAdmin APIとProxyのアドレスを環境変数で設定する。
筆者は今回はtype: LoadBalancerなどを使わずクラスタ内からアクセスしたため、以下のようにServiceを指定した。

ADMINAPI=http://kong-aws-cp-kong-admin:8001
PROXY=http://kong-aws-cp-kong-proxy:80

Service、Route、Pluginを設定する。

curl -s -X POST ${ADMINAPI}/services \
  -H "Content-Type: application/json" \
  -d '{
    "name":"httpbin-svc",
    "url":"https://httpbin.org"
  }'
curl -s -X POST ${ADMINAPI}/services/httpbin-svc/routes \
  -H "Content-Type: application/json" \
  -d '{
    "name":"httpbin-rt",
    "paths":["/httpbin"]
  }'
curl -s -X POST ${ADMINAPI}/routes/httpbin-rt/plugins \
  -d name=dao-test

以上で検証の準備は整った。

続いて検証を行う。
テーブルを参照するためにまずPostgresのパスワードを環境変数に設定する。

PGPASSWORD=$(kubectl get secret -n kong kong-aws-cp-postgresql -o jsonpath={.data.password} | base64 -d)

設定したパスワードを使ってテーブルを参照する。

kubectl exec -it kong-aws-cp-postgresql-0 -- env PGPASSWORD=$PGPASSWORD psql -U kong -d kong -c "SELECT * FROM my_plugin_table;"

まだDBを操作するようなリクエストを投げていないため、テーブル内は空である。

 id | created_at | mykey
----+------------+-------
(0 rows)

次にDBにInsertするようなリクエストを発行する。

curl $PROXY/httpbin/ip -H mykey-add:test

再度テーブルを確認すると以下のように反映された。

                  id                  |     created_at      | mykey
--------------------------------------+---------------------+-------
 8c6d489b-b3cb-447d-a4ed-90f655e3ada0 | 2025-01-07 04:02:09 | test

Kubernetes上でも問題なくカスタムエンティティを利用することが出来た。
なお、途中でも触れたようにHybridモードではカスタムエンティティは更新できない。
KubernetesだとDBlessやHybridモードで展開する事が多いと思うので、そもそも要件やアーキテクチャ的に使えるのかどうかを確認した上で利用した方がよい。

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?