はじめに
KubernetesではJobやCronJobが用意されていますが、ジョブ内容によってはLambdaに寄せてもよい場合があります。
今回はEKSクラスタに対するkubectl操作をLambdaから実施するための手順を説明します。
設定手順
Lambda Layerのデプロイ
AWSコンソールのLambdaのページから作成していきます。
Serverless Application Repositoryからlambda-layer-kubectlを選択します。
IAM Roleの作成
Lambda関数で使用するIAM Roleをlambda-kubectl
という名前で作成します。
EKSの権限を持つ以下のようなIAM Policyをアタッチします。
{
"Version": "2012-10-17",
"Statement": [
{
"Action": [
"ec2:*",
"eks:*"
],
"Resource": "*",
"Effect": "Allow"
}
]
}
また、信頼関係には以下のようにLambdaサービスを入れておきます。
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Principal": {
"Service": "lambda.amazonaws.com"
},
"Action": "sts:AssumeRole"
}
]
}
aws-authの更新
以下のようにaws-authを編集しapplyします。
apiVersion: v1
data:
mapRoles: |
+ - rolearn: 'arn:aws:iam::XXXXXXXXXXXX:role/lambda-kubectl'
+ username: 'lambda-kubectl'
+ groups:
+ - 'system:masters'
kind: ConfigMap
metadata:
name: aws-auth
namespace: kube-system
$ kubectl apply -f aws-auth.yaml
Lambda関数の作成
Lambda Layer同様、AWSコンソールのLambdaのページから作成していきます。
カスタムランタイムを使用し、先述のIAM Roleを付与します。
bootstrap
にkubectlの処理を追記します。
#!/bin/sh
set -euo pipefail
# Handler format: <script_name>.<bash_function_name>
#
# The script file <script_name>.sh must be located at the root of your
# function's deployment package, alongside this bootstrap executable.
source $(dirname "$0")/"$(echo $_HANDLER | cut -d. -f1).sh"
while true
do
+ export PATH=$PATH:/opt/awscli:/opt/kubectl
+ aws eks update-kubeconfig --name test-cluster --kubeconfig /tmp/kubeconfig
+ kubectl get node --kubeconfig /tmp/kubeconfig
# Request the next event from the Lambda runtime
HEADERS="$(mktemp)"
EVENT_DATA=$(curl -v -sS -LD "$HEADERS" -X GET "http://${AWS_LAMBDA_RUNTIME_API}/2018-06-01/runtime/invocation/next")
INVOCATION_ID=$(grep -Fi Lambda-Runtime-Aws-Request-Id "$HEADERS" | tr -d '[:space:]' | cut -d: -f2)
# Execute the handler function from the script
RESPONSE=$($(echo "$_HANDLER" | cut -d. -f2) "$EVENT_DATA")
# Send the response to Lambda runtime
curl -v -sS -X POST "http://${AWS_LAMBDA_RUNTIME_API}/2018-06-01/runtime/invocation/$INVOCATION_ID/response" -d "$RESPONSE"
done
確認
Lambdaのテストイベントでジョブを実行してみます。
関数で定義したようにEKSに対して操作できていることが確認できます。
まとめ
LambdaからEKSを操作する方法を説明しました。
使用したLambda Layerのlambda-layer-kubectlにはAWS CLIやkubectlの他、helmやjqも同梱されているので汎用性が高いです。
EKSがprivateである場合はLambdaを同一VPC内で実行するようにしましょう。