Closed4

K8s環境で任意のシェルスクリプトを実行するCronjob/Jobを作りたい

harrythecodeharrythecode

やりたいこと

K8s環境で任意のシェルスクリプトを実行するCronjob/Jobを作りたい。追加でkubectlコマンドを実行してその結果を反映させたい。

harrythecodeharrythecode

完成形

以下は毎時0時(UTC)に、Postman ECHOへcurlし、K8sのnamespaceを取得してechoするだけのcronjobです。

arbitrary-script.yaml
apiVersion: v1
kind: ServiceAccount
metadata:
  name: cronjob-serviceaccount
---
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
  name: cronjob-clusterrole
rules:
- apiGroups: ["*"]
  resources: ["*"]
  verbs: ["get", "list"]
---
kind: ClusterRoleBinding
apiVersion: rbac.authorization.k8s.io/v1
metadata:
  name: cronjob-clusterrolebinding
subjects:
  - kind: ServiceAccount
    name: cronjob-serviceaccount
    namespace: default
    apiGroup: ""
roleRef:
  kind: ClusterRole
  name: cronjob-clusterrole
  apiGroup: ""
---
apiVersion: batch/v1
kind: CronJob
metadata:
  name: run-arbitrary-script-cronjob
spec:
  schedule: "0 0 * * *"
  jobTemplate:
    spec:
      parallelism: 1
      completions: 1
      template:
        metadata:
          name: run-arbitrary-script-cronjob
        spec:
          serviceAccountName: cronjob-serviceaccount
          volumes:
          - name: scripts-volume
            configMap:
              name: run-arbitrary-script
          containers:
          - name: run-arbitrary-script
            image: alpine
            volumeMounts:
              - mountPath: /scripts
                name: scripts-volume
            env:
              - name: HOME
                value: /tmp
              - name: ENV
                value: development
              # - name: SECRET
              #   valueFrom:
              #     secretKeyRef:
              #       name: any-secret-whatever-you-want
              #       key: SECRET
            command:
            - /bin/sh
            - -c
            - |
              cp /scripts/*.sh /tmp
              chmod +x /tmp/*.sh
              /tmp/bootstrap.sh
              /tmp/run-arbitrary-script.sh $ENV
          restartPolicy: Never
---
apiVersion: v1
kind: List
items:
- apiVersion: v1
  kind: ConfigMap
  metadata:
    name:  run-arbitrary-script
  data:
    bootstrap.sh: |
      echo "=== Initialization"
      apk add --no-cache --virtual=build-deps wget \
        && wget https://storage.googleapis.com/kubernetes-release/release/v1.23.0/bin/linux/amd64/kubectl \
        && mv kubectl /usr/local/bin/kubectl \
        && chmod +x /usr/local/bin/kubectl \
        && apk del build-deps
      apk add --no-cache jq bash curl
    run-arbitrary-script.sh: |
      #!/bin/bash
      ENV=$1
      echo "=== run-arbitrary-script.sh"
      curl -s "https://postman-echo.com/get?env=$ENV"|jq .args
      namespaces=(`kubectl get namespace --no-headers -o custom-columns=":metadata.name"`)
      for namespace in "${namespaces[@]}"
      do
        echo $namespace
      done
$ kubectl create -f arbitrary-script.yaml
serviceaccount/cronjob-serviceaccount created
clusterrole.rbac.authorization.k8s.io/cronjob-clusterrole created
clusterrolebinding.rbac.authorization.k8s.io/cronjob-clusterrolebinding created
cronjob.batch/run-arbitrary-script-cronjob created
configmap/run-arbitrary-script created

# 手動でcronjobをトリガーする
$ kubectl create job --from=cronjob/run-arbitrary-script-cronjob run-arbitrary-script-cronjob-manually
job.batch/run-arbitrary-script-cronjob-manually created

$ kubectl get pod
NAME                                          READY   STATUS    RESTARTS   AGE
run-arbitrary-script-cronjob-manually-94qb9   1/1     Running   0          8s

$ kubectl logs run-arbitrary-script-cronjob-manually-94qb9
...
OK: 11 MiB in 25 packages
=== run-arbitrary-script.sh
{
  "env": "development"
}
default
kube-node-lease
kube-public
kube-system
harrythecodeharrythecode

補足

  • kubectlコマンド等はalpine(何も入ってない最小のLinuxイメージ)に都度インストールして使えるようにしています。
  • 任意のスクリプトをconfigmapに入れて保存することでK8s定義ファイルだけで自由にカスタマイズできるようにしています。
  • Service Accountは意図的に全てのリソースに対してアクセス権限を持たせてます。実運用の際には適宜変更してご利用ください。
  • bootstrap.sh部分をコンテナ化する際には以下のサイトが便利です。

https://qiita.com/pottava/items/452bf80e334bc1fee69a

このスクラップは2022/10/18にクローズされました