본문 바로가기
데브옵스 이야기

stakater/Reloader 사용시 configmap, secret 변경할 시에 감지 안되는 이슈

by lakescript 2025. 12. 22.
728x90

 

 

 

K8s 운영 과정에서 ConfigMap/Secret 변경 시 Pod를 재기동하는 것은 꼭 필요한 프로세스입니다.

다만 사람이 수동으로 처리하기 어렵기 때문에, 보통은 Helm 템플릿 + checksum annotation(`checksum/config`) 방식으로 ConfigMap/Secret 변경을 감지해 자동으로 Rolling Update가 일어나도록 구성합니다.

 

하지만 사내에서는 아직 Helm을 도입하지 않았고(준비중), Kustomize를 활용하여 리소스를 관리하고 있기 때문에 오픈소스인 stakater/reloader를 도입해 ConfigMap/Secret 변경 시 워크로드를 자동으로 재배포하도록 운영하고 있습니다.

 

그런데 운영 중 ConfigMap이 변경되었음에도 간헐적으로 Pod가 재시작되지 않는 현상이 발생했고, 이를 명확히 파악하기 위해 테스트 환경을 구성하여 검증을 진행했습니다.

 

 

테스트 시나리오 및 전체 플로우 요약

1. ConfigMap 변경이 정상적으로 감지되는지

2. 감지되었다면, 워크로드가 정상적으로 롤링 업데이트(또는 재시작) 되는지

2-1.감지는 되는데 재시작이 안 된다면

  • Reloader의 롤아웃 전략 설정 문제
    • Rollout/Deployment 리소스 종류에 따른 처리 방식 차이
  • ArgoCD가 drift로 인식하여 적용을 되돌리거나 충돌하는 문제

2-2. 감지 자체가 안 된다면

  • Reloader 리소스 라벨/annotation 매칭 문제
  • Helm 도입 + checksum annotation 방식 검토

위 목표 및 가설을 토대로 테스트를 진행하였습니다.

 

 

환경 구성

reloader 설정 수정 (slack webhook 발송)

 
...
  ALERT_ON_RELOAD: "true"
    ALERT_SINK: "slack"
    ALERT_WEBHOOK_URL: webhook url
    ALERT_ADDITIONAL_INFO: "configmap-reloader 알람 (재시작 발생하는지 확인용)"
...

 

위와 같이 configmap reloader에서 감지되면 slack으로 메시지를 보내게끔 설정했습니다.

 

Test Pod의 Configmap 수정

apiVersion: v1
kind: ConfigMap
metadata:
  name: dev-reloader-test-configmap
  annotations:
    reloader.stakater.com/match: "true" 
data:
  TEST_VALUE: "initial-value-1"
  TEST_TIMESTAMP: "2024-01-01T00:00:00Z"
  TEST_DESCRIPTION: "ConfigMap Reloader 테스트용 ConfigMap"

 

초기에 구성한 configmap입니다.

`reloader.stakater.com/match: "true"`로 Reloader가 변경을 감지할 수 있도록 구성하였고, 테스트를 진행하면서 해당 값들이 변경되는것을 의도하였습니다.

 

Test Pod yaml 수정

...
    spec:
      nodeSelector:
       dedicate: worker
      containers:
        - name: reloader-test
          image: busybox:1.36
          command:
            - sh
            - -c
            - |
              echo "=== ConfigMap Reloader Test Pod 시작 ==="
              echo "Pod 시작 시간: $(date -u +%Y-%m-%dT%H:%M:%SZ)"
              echo "TEST_VALUE: $TEST_VALUE"
              echo "TEST_TIMESTAMP: $TEST_TIMESTAMP"
              echo "TEST_DESCRIPTION: $TEST_DESCRIPTION"
              echo "Pod UID: $(cat /proc/self/cgroup | grep -oP 'docker/\K[^/]+' || echo 'unknown')"
              echo "=== 환경변수 확인 완료 ==="
              # ConfigMap 변경 감지를 위해 주기적으로 로그 출력
              while true; do
                echo "[$(date -u +%Y-%m-%dT%H:%M:%SZ)] Pod 실행 중... TEST_VALUE=$TEST_VALUE"
                sleep 30
              done
...

 

위와 같이 busybox image를 받아와 configmap의 값을 로그로 출력하는 pod를 구성합니다.

 

Test Pod 배포 후 log 확인

 

위에 구성한 pod를 배포한 후 log를 확인해보면 위와 같이 현재의 `TEST_VALUE=initial-value-1` 값을 출력하고 있는 것을 확인할 수 있습니다.

 

1차 테스트 진행 (configmap 수정)

configmap 수정

...
  data:
    TEST_VALUE: "updated-value-2"
    TEST_TIMESTAMP: "2024-12-19T12:00:00Z"
    TEST_DESCRIPTION: "ConfigMap Reloader 테스트용 ConfigMap - 수정됨"
...

 

위와 같이 값을 수정하고 확인해보겠습니다.

 

slack 확인

 

위와 같이 slack 메시지가 정상적으로 오는 것을 확인했습니다.

 

 

Reloader log 확인

 

Changes detected in 'dev-reloader-test-configmap' of type 'CONFIGMAP' in namespace 'dev-reloader-test'; updated 'dev-reloader-test' of type 'Rollout' in namespace 'dev-reloader-test'"

 

reloader pod에서 위의 로그가 쌓여 감지는 정상적으로 이루어진 것을 확인할 수 있었습니다.

 

Test Pod log 확인

 

 

 

하지만 pod가 정상적으로 재시작되지 않았고, 그에 따라 configmap도 이전의 configmap이 보여집니다.

 

1차 테스트 결론

현재 감지는 되지만, 재배포가 이루어지지 않음

 

가설 : ArgoCD 환경에서 기본 전략이 drift로 감지될 수 있음

 

 

 

해당 오픈소스의 공식문서를 확인해보면, ArgoCD 환경에서는 기본 rollout 전략이 `configuration drift` 로 감지될 수 있어 `restart` 전략을 사용해야 한다고 합니다.

(즉, Reloader가 워크로드에 변화를 주더라도 ArgoCD가 이를 “원하지 않는 변경”으로 보고 되돌리거나 충돌할 수 있음)

 

2차 테스트 진행 (Rollout Strategy를 restart로 변경)

Test Pod 수정

...
  annotations:
    reloader.stakater.com/auto: "true"
    reloader.stakater.com/rollout-strategy: "restart"
...

 

pod의 annotation에 `rollout-strategy: “restart”` 를 추가하여, 기본 배포 방식을 rolling update에서 restart로 변경합니다.

 

 

Test Pod log 확인

 

이전에 수정했었던 `TEST_VALUE=updated-value-2` 이 출력되고 있는 것을 확인할 수 있습니다.

 

Test Pod ConfigMap 수정

...
  TEST_VALUE: "updated-value-3"
  TEST_TIMESTAMP: "2024-12-19T14:30:00Z"
  TEST_DESCRIPTION: "ConfigMap Reloader 테스트용 ConfigMap - 2차 수정 (restart 전략 테스트)"
...

 

 

Slack으로 Reloader 감지 확인

 
정상적으로 감지된 것을 slack 메시지를 통해 확인할 수 있었습니다.
 
 

ArgoCD에서 Application 확인

 

그 후 ArgoCD에서 해당 Test Application을 확인해보면 pod가 재시작되고 있는 것을 확인할 수 있습니다.

 

 

2차 테스트 결론

restart로 배포 방식을 변경하면 configmap이 수정될 시에 재시작됨.

 

restart 전략은 원하는 흐름대로 동작합니다. 하지만 restart 전략을 운영 환경에서 사용한다면 매우매우 리스크가 큽니다.(당연히...)

 

대안: reloadStrategy를 annotations로 설정하여 drift 회피 + rolling update 유도

Reload Strategies

 

 

그렇게 테스트를 진행하면서 해당 이슈를 해결하기 위해 공식문서를 보던 중 `--reload-strategy=annotations` 을 `configmap-reloader` 에 설정하면 ArgoCD drift를 피하면서도 rolling update가 가능하다고 합니다. (오!!!)

 

3차 테스트 - reloadStrategy를 annotations로 설정

reloader 설정 변경

...
  isArgoRollouts: true
  reloadStrategy: "annotations"
...
 

 

Test Pod의 Configmap 수정

...
  TEST_VALUE: "updated-value-5-rolling-update-test"
  TEST_TIMESTAMP: "2024-12-19T17:00:00Z"
  TEST_DESCRIPTION: "ConfigMap Reloader 테스트용 ConfigMap - rolling update 테스트"
...

 

이전에 설정했던 restart는 삭제하고, configmap을 수정합니다.

 

결과

 

그 후 ArgoCD에서 확인해보면 rolling upgrdate 방식으로 배포가 이루어지는 것을 확인할 수 있었습니다.

 

 

또한, 로그도 수정된 configmap으로 쌓이는 것을 확인할 수 있었습니다.

 

 

Pod의 상세 내용을 확인해보면, 이전에 없던 annotation이 생성된 것을 확인할 수 있tmqslek.

이는 설정한 reload-strategy으로 인해 pod에 설정된 annotation인데, 해당 설정을 통해 마지막 수정날짜를 확인해서 ArgoCD에서 diff 인식하게끔 만들고 rolloing upgrade 트리거로 동작하게끔 동작합니다.

 

결론

현재 구성된 Slack 알림 및 reloader 로그를 통해 확인해본 결과 Reloader는 ConfigMap 변경을 정상적으로 감지했습니다. 하지만 이 이슈의 근본적인 문제는 configmap 변경의 감지에 대한 것이 아닌 아닌, ArgoCD 환경에서 실제 롤아웃이 누락될 수 있음이었습니다.

 

대응 방안으로 `rollout-strategy: restart` 는 재시작을 확실하게 트리거한다는 장점이 있지만, 운영 환경에서는 트래픽 단절 등 가용성 측면의 리스크가 있어 신중한 적용이 필요했기에 사용할 수 없습니다.

 

반면 `reloadStrategy: annotations` 는 ArgoCD의 drift 문제를 회피하면서도 Rolling Update를 유도할 수 있는 방식으로, 운영 환경에서도 충분히 현실적인 대안이 될 수 있었고, 테스트를 통해 적절한 대안인 것을 확인할 수 있었습니다.

 

사실 Helm을 사용한다면 checksum을 통해 더 쉽게 configmap/secret 변경을 감지해서 Pod를 재시작할 수 있습니다. 

 

stakater/Reloader을 사용하시면서 이와 같은 이슈를 만나신 분들은 이러한 시행착오가 도움이 되셨으면 좋겠습니다.

728x90