ミクシィグループ Advent Calendar 2020 の25日目の投稿です。
こんにちは, @Taillookです。
普段の業務ではRailsやGo,React,GKEなどを触っています。
はじめに
k8sのマニフェストをGitリポジトリで扱う場合、secretの情報をセキュアな状態で管理する必要があります。
自分はkubesec,SealedSecretをこれまでに使ってきましたがkubesecではArgoCD等を使ったGitOpsとの併用がしづらかったり、SealedSecretでは暗号化後のファイルのレビューができないという理由で別の手段を探していました。
今回これらを解決する手段としてkubernetes-external-secretsがあると知り導入してみました。
kubernetes-external-secretsとは
Kubernetes External Secrets — GoDaddy Engineering Blog
kubernetes-external-secretsはGoDaddyのチームが開発した、AWSのSecret Manager等、k8sのクラスタ外部にあるsecret情報にアクセスしk8sのsecretとして扱うようにするソリューションです。
GKEへの導入
本家のHelmChartを手元にダウンロード
(これを使い続けるのはvertion追従しづらいので最新のmasterのChartを取得するコマンドを書いておくとよさそうです。
サービスアカウントの追加
Secret Managerのsecretmanager.versions.access
権限のあるサービスアカウントを追加します。
kubernetes-external-secretsのChartにGCP Secret Managerのためのsecretを追加する
external-secretsのためのsecretsを設定するためGit管理できるようにテンプレートから生成できるようにします。
apiVersion: v1
kind: Secret
metadata:
name: external-secrets-secret
type: Opaque
stringData:
gcp-creds.json: |-
service_account_key.json
という名前で先ほど追加したサービスアカウントの鍵のjsonを作成し以下スクリプトでテンプレートからsecretのyamlを生成するようにしました。
#!/bin/sh
sed -i '' 's/^/ /g' service_account_key.json && cat service_account_key.json >> secret.yaml.template && cp secret.yaml.template secret.yaml
valuesにexternal-secrets-secretを追加する
valuesにある
# GOOGLE_APPLICATION_CREDENTIALS: /app/gcp-creds/gcp-creds.json
と
# filesFromSecret:
# gcp-creds:
# secret: gcp-creds
# mountPath: /app/gcp-creds
のコメントを外し/app/gcp-creds/gcp-creds.json
に設定したexternal-secrets-secretをマウントしGOOGLE_APPLICATION_CREDENTIALSから参照できるようにします。
この状態で
#!/bin/sh
helm install external-secrets ./chart --skip-crds
を実行しexternal-secretsをインストールします
secretを適用する
GCP Secret Managerで画像のようにシークレットを作成します。
作成したシークレットの名前で以下のyamlのsecretが適用できます。
dataのkeyはGCPのSecret Managerで設定したシークレットの名前で、nameはk8sのsecretでの名前になり、versionが同一シークレット名内でのバージョンとなります。バージョンはlatestでも指定できます。
apiVersion: kubernetes-client.io/v1
kind: ExternalSecret
metadata:
name: gcp-secrets-manager-example
spec:
backendType: gcpSecretsManager
projectId: GCP-project
data:
- key: GCP_PROJECT_RAILS_ENV
name: RAILS_ENV
version: 1
これでk8s内でsecretとして扱えるようになります。
まとめ
SealedSecretと比較して、key: GCP_PROJECT_RAILS_ENV
のように記述でき、GCPコンソール上で平文で確認もできるのでyamlのレビューが可能になったので読めない文字列のapproveをしてsecret適用できなかった!という事態も少なくなり治安も良くなりました。
kubesecとの比較としてもsecretへの変換をk8s上でハンドルできるのでArgoCDを使ったGitOpsの相性が良くなる利点もあります。
GKEやKubernetesについてはまだまだ勉強不足なのでより深く知れたら良いなと常々感じています。
来年はKubernetes周りのコードリーディングとかしてみたいです。