AWS Secrets Manager のシークレットを Kubernetes Pod にマウントする
AWS Secrets Manager のシークレットを保存し、Kubernetes のシークレットと同期したので、そのシークレットを Pod の中にマウントしてみましょう。まず、catalog デプロイメントと catalog 名前空間に存在するシークレットを確認しましょう。
現在、catalog デプロイメントは、環境変数を通じて catalog-db シークレットからデータベースの認証情報にアクセスしています:
RETAIL_CATALOG_PERSISTENCE_USERRETAIL_CATALOG_PERSISTENCE_PASSWORD
これは、envFrom を使用してシークレットを参照することで行われています:
- configMapRef:
name: catalog
- secretRef:
name: catalog-db
catalog デプロイメントには現在、/tmp にマウントされている emptyDir 以外の追加の volumes や volumeMounts はありません:
- emptyDir:
medium: Memory
name: tmp-volume
- mountPath: /tmp
name: tmp-volume
AWS Secrets Manager に保存されているシークレットを認証情報のソースとして使用するように catalog デプロイメントを変更しましょう:
- Kustomize Patch
- Deployment/catalog
- Diff
apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization
resources:
- ../../../../base-application/catalog
patches:
- path: deployment.yaml
- path: serviceaccount.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
labels:
app.kubernetes.io/created-by: eks-workshop
app.kubernetes.io/type: app
name: catalog
namespace: catalog
spec:
replicas: 1
selector:
matchLabels:
app.kubernetes.io/component: service
app.kubernetes.io/instance: catalog
app.kubernetes.io/name: catalog
template:
metadata:
annotations:
prometheus.io/path: /metrics
prometheus.io/port: "8080"
prometheus.io/scrape: "true"
labels:
app.kubernetes.io/component: service
app.kubernetes.io/created-by: eks-workshop
app.kubernetes.io/instance: catalog
app.kubernetes.io/name: catalog
spec:
containers:
- env:
- name: RETAIL_CATALOG_PERSISTENCE_USER
valueFrom:
secretKeyRef:
key: username
name: catalog-secret
- name: RETAIL_CATALOG_PERSISTENCE_PASSWORD
valueFrom:
secretKeyRef:
key: password
name: catalog-secret
envFrom:
- configMapRef:
name: catalog
image: public.ecr.aws/aws-containers/retail-store-sample-catalog:1.2.1
imagePullPolicy: IfNotPresent
livenessProbe:
httpGet:
path: /health
port: 8080
initialDelaySeconds: 30
periodSeconds: 3
name: catalog
ports:
- containerPort: 8080
name: http
protocol: TCP
readinessProbe:
httpGet:
path: /health
port: 8080
periodSeconds: 5
successThreshold: 3
resources:
limits:
memory: 512Mi
requests:
cpu: 250m
memory: 512Mi
securityContext:
capabilities:
drop:
- ALL
readOnlyRootFilesystem: true
runAsNonRoot: true
runAsUser: 1000
volumeMounts:
- mountPath: /etc/catalog-secret
name: catalog-secret
readOnly: true
- mountPath: /tmp
name: tmp-volume
securityContext:
fsGroup: 1000
serviceAccountName: catalog
volumes:
- csi:
driver: secrets-store.csi.k8s.io
readOnly: true
volumeAttributes:
secretProviderClass: catalog-spc
name: catalog-secret
- emptyDir:
medium: Memory
name: tmp-volume
app.kubernetes.io/instance: catalog
app.kubernetes.io/name: catalog
spec:
containers:
- - envFrom:
+ - env:
+ - name: RETAIL_CATALOG_PERSISTENCE_USER
+ valueFrom:
+ secretKeyRef:
+ key: username
+ name: catalog-secret
+ - name: RETAIL_CATALOG_PERSISTENCE_PASSWORD
+ valueFrom:
+ secretKeyRef:
+ key: password
+ name: catalog-secret
+ envFrom:
- configMapRef:
name: catalog
- - secretRef:
- name: catalog-db
image: public.ecr.aws/aws-containers/retail-store-sample-catalog:1.2.1
imagePullPolicy: IfNotPresent
livenessProbe:
httpGet:
[...]
readOnlyRootFilesystem: true
runAsNonRoot: true
runAsUser: 1000
volumeMounts:
+ - mountPath: /etc/catalog-secret
+ name: catalog-secret
+ readOnly: true
- mountPath: /tmp
name: tmp-volume
securityContext:
fsGroup: 1000
serviceAccountName: catalog
volumes:
+ - csi:
+ driver: secrets-store.csi.k8s.io
+ readOnly: true
+ volumeAttributes:
+ secretProviderClass: catalog-spc
+ name: catalog-secret
- emptyDir:
medium: Memory
name: tmp-volume
CSI ドライバーを使用して AWS Secrets Manager シークレットをマウントし、以前に検証した SecretProviderClass を使用して、Pod 内の /etc/catalog-secret マウントパスにマウントします。これにより、AWS Secrets Manager は保存されたシークレットの内容を Amazon EKS と同期し、Pod 内で環境変数として消費できる Kubernetes シークレットを作成します。
catalog 名前空間で行われた変更を確認しましょう。
デプロイメントには、CSI Secret Store ドライバーを使用する新しい volume と対応する volumeMount が追加され、/etc/catalog-secret にマウントされています:
- csi:
driver: secrets-store.csi.k8s.io
readOnly: true
volumeAttributes:
secretProviderClass: catalog-spc
name: catalog-secret
- emptyDir:
medium: Memory
name: tmp-volume
- mountPath: /etc/catalog-secret
name: catalog-secret
readOnly: true
- mountPath: /tmp
name: tmp-volume
マウントされたシークレットは、Pod のコンテナファイルシステム内にファイルとして機密情報にアクセスする安全な方法を提供します。このアプローチには、環境変数としてシークレット値を公開しないことや、ソースシークレットが変更されたときに自動更新されるなど、いくつかの利点があります。
Pod 内部でマウントされたシークレットの内容を調べてみましょう:
eks-workshop-catalog-secret-WDD8yS
password
username
{"username":"catalog", "password":"dYmNfWV4uEvTzoFu"}catalog
dYmNfWV4uEvTzoFu
CSI ドライバーを使用して AWS Secrets Manager からシークレットをマウントすると、マウントパスに 3 つのファイルが作成されます:
- AWS シークレットの名前を持つファイルで、完全な JSON 値が含まれます
- SecretProviderClass で定義された jmesPath 式を通じて抽出された各キーの個別ファイル
環境変数は、CSI Secret Store ドライバーを介して SecretProviderClass によって自動的に作成された catalog-secret から取得されるようになりました:
- name: RETAIL_CATALOG_PERSISTENCE_USER
valueFrom:
secretKeyRef:
key: username
name: catalog-secret
- name: RETAIL_CATALOG_PERSISTENCE_PASSWORD
valueFrom:
secretKeyRef:
key: password
name: catalog-secret
NAME TYPE DATA AGE
catalog-db Opaque 2 15h
catalog-secret Opaque 2 43s
実行中の Pod で環境変数が正しく設定されていることを確認できます:
RETAIL_CATALOG_PERSISTENCE_ENDPOINT=catalog-mysql:3306
RETAIL_CATALOG_PERSISTENCE_PASSWORD=dYmNfWV4uEvTzoFu
RETAIL_CATALOG_PERSISTENCE_PROVIDER=mysql
RETAIL_CATALOG_PERSISTENCE_DB_NAME=catalog
RETAIL_CATALOG_PERSISTENCE_USER=catalog
これで AWS Secrets Manager と完全に統合された Kubernetes シークレットがあり、シークレット管理のベストプラクティスであるシークレットのローテーションを活用できます。AWS Secrets Manager でシークレットがローテーションまたは更新されると、デプロイメントの新しいバージョンをロールアウトして、CSI Secret Store ドライバーが Kubernetes シークレットの内容を更新された値と同期できるようにすることができます。