[kubernetes-event-exporter] 오래된 쿠버네티스 이벤트 조회
쿠버네티스에서 애플리케이션 트러블슈팅을 할 때 쿠버네티스 이벤트(Kubernetes event)가 단서를 제공하는 경우가 많다. 하지만 etcd의 저장 공간 제한 때문에 길어도 며칠 정도밖에 보관되지 않아 시간이 지나면 이벤트를 확인할 수 없어서 원인 파악이 어려워지는 문제가 있다.
kubernetes-event-exporter를 활용하면 이벤트를 로그로 남겨 AWS CloudWatch Logs 나 Elasticsearch 같은 로그 처리 시스템에 저장하고 필요할 때 조회할 수 있다.
Note: 쿠버네티스 이벤트는 kubectl get event
, kubectl describe
명령으로 확인할 수 있다.
kubernetes-event-exporter
https://github.com/resmoio/kubernetes-event-exporter/blob/master/README.md
위 가이드에선 이벤트를 모니터링해서 통보하는 설정을 좀 더 비중있게 다루고 있으나 이벤트는 로그로 남기는 것이 더 적합한 것 같다. 모니터링은 Prometehus metric 같은 것으로 하고 문제의 원인을 파악할 때 이벤트 로그를 꺼내보면 된다.
예제 구성
AWS의 CloudWatch Logs를 활용하는 예제이다.
- kubernetes-event-exporter는 표준 출력(standard output)으로 이벤트의 로그를 남긴다. 로그는 JSON 형식이다.
- DaemonSet으로 실행되는 fluent-bit가 kubernetes-event-exporter 의 표준 출력을 CloudWatch Logs로 전송한다.
- CloudWatch Logs Insights 의 쿼리를 사용해 문제가 발생한 시점의 이벤트를 조회한다.
Helm 차트 설치 방법
Bitnami에서 제공하는 Helm 차트를 설치하는 방법이다.
Note: 차트 버전 1.5.2 에서 테스트했으며 이 포스트를 쓰는 시점의 최신 차트 버전인 2.0.0 까지는 같은 방식으로 해야 하는 것을 확인했다.
아래 명령으로 설치할 수 있다.
1helm repo add bitnami https://charts.bitnami.com/bitnami
2
3helm upgrade event-exporter bitnami/kubernetes-event-exporter \
4 --install \
5 --create-namespace \
6 --namespace event-exporter \
7 --version 1.5.2 \
8 --values values.yaml
9
10kubectl apply -f more-rbac.yaml
values.yaml
내용 :
1image:
2 repository: public.ecr.aws/bitnami/kubernetes-event-exporter
3rbac:
4 create: true # view ClusterRole 을 바인딩하는데 이 권한만으론 부족함. more-rbac.yaml에서 권한을 추가로 부여한다.
5
6config:
7 logLevel: info
8 route:
9 routes:
10 - match:
11 - receiver: "dump"
12 receivers:
13 - name: "dump"
14 stdout: { }
15resources:
16 requests:
17 cpu: 10m
18 memory: 100Mi
more-rbac.yaml
내용:
1apiVersion: rbac.authorization.k8s.io/v1
2kind: ClusterRole
3metadata:
4 name: event-exporter
5rules:
6- apiGroups:
7 - ""
8 resources:
9 - nodes
10 verbs:
11 - get
12 - list
13 - watch
14---
15apiVersion: rbac.authorization.k8s.io/v1
16kind: ClusterRoleBinding
17metadata:
18 name: event-exporter
19roleRef:
20 apiGroup: rbac.authorization.k8s.io
21 kind: ClusterRole
22 name: event-exporter
23subjects:
24 - kind: ServiceAccount
25 name: event-exporter
26 namespace: event-exporter
values.yaml 설명
쿠버네티스의 표준적인 방법대로 로그를 표준 출력으로 내보내게 설정한다. 아래 문서의 가이드대로 config 차트 파라미터를 설정하고 있다.
https://github.com/resmoio/kubernetes-event-exporter/blob/master/README.md#stdout
이렇게 설정하면 로그가 아래처럼 JSON형식으로 출력된다.
1{"metadata":{"name":"kube-proxy-hcctq.171fa332d0d2fca1","namespace":"kube-system","uid":"813df6a8-d912-49a1-9fa6-2d74b061a66f","resourceVersion":"311176937","creationTimestamp":"2022-10-20T01:37:05Z"},"reason":"NodeNotReady","message":"Node is not ready","source":{"component":"node-controller"},"firstTimestamp":"2022-10-20T01:37:05Z","lastTimestamp":"2022-10-20T01:37:05Z","count":1,"type":"Warning","eventTime":null,"reportingComponent":"","reportingInstance":"","involvedObject":{"kind":"Pod","namespace":"kube-system","name":"kube-proxy-hcctq","uid":"19adea83-7bec-4bd4-918d-ddc39e6c4c45","apiVersion":"v1","resourceVersion":"311176399","labels":{"controller-revision-hash":"f6b68b794","k8s-app":"kube-proxy","pod-template-generation":"4"}}}
Note: 만약 config
파라미터를 설정하지 않으면 아래와 같이 로그의 내용이 빈 상태로 출력된다.
1{}
Helm 차트를 설치하면 아래처럼 기본 설정으로 이벤트를 표준 출력에 덤프한다는 메시지가 출력된다. 이 내용에 따르면 차트 파라미터를 따로 설정할 필요가 없는 것처럼 보이지만 실제로는 그렇지 않으니 주의해야 한다.
1By default, the kubernetes-event-exporter will dump events to stdout.
2To configure additional endpoints, redeploy the chart overwritting the field 'config' at your 'values.yml'.
more-rbac.yaml 설명
values.yaml에서 rbac 파라미터를 true로 설정하면 view ClusterRole을 사용한다. 그런데 그것만으론 권한이 부족헤 kubernetes-event-exporter의 로그에 아래와 같은 에러가 남은다. 부족한 권한을 more-rbace.yaml 로 부여하는 것이다.
12022-10-12T23:35:24Z ERR bitnami/blacksmith-sandox/kubernetes-event-exporter-0.11.0/src/github.com/opsgenie/kubernetes-event-exporter/pkg/kube/watcher.go:75 > Cannot list labels of the object error="nodes \"ip-10-255-14-142.ap-northeast-2.compute.internal\" is forbidden: User \"system:serviceaccount:event-exporter:event-exporter-kubernetes-event-exporter\" cannot get resource \"nodes\" in API group \"\" at the cluster scope"
more-rbac.yaml의 예제에선 nodes에 대한 권한을 부여하고 있는데 클러스터 설정에 따라 권한을 더 부여해야 할 수도 있다.
FluentBbit 로 AWS CloudWatch Logs 로 로그 전송
AWS CloudWatch Logs 에 application 로그를 전송하려면 아래 가이드를 따르면 된다. https://docs.aws.amazon.com/AmazonCloudWatch/latest/monitoring/Container-Insights-setup-logs-FluentBit.html
이 가이드대로 FluentBit를 설정하면 로그 내용이 JSON 형식일 때 그 내용을 log_processed
필드로 쿼리할 수 있다. 다음 섹션의 쿼리 예제를 참고한다.
CloudWatch Logs 에서 로그를 조회하는 예제
아래처럼 CloudWatch Logs Insights 쿼리로 검색할 수 있다.
우선 조회할 로그 그룹을 /aws/containerinsights/<cluster-name>
/application 으로 설정한다.
아래처럼 쿼리를 실행하면 된다.
1fields @timestamp, log_processed.involvedObject.kind as kind,
2 log_processed.involvedObject.namespace as namespace,
3 log_processed.involvedObject.name as object_name, log_processed.message as message
4| filter kubernetes.container_name = 'event-exporter' and kind = 'Pod'
5| sort @timestamp asc
결과는 아래와 같다.
Note: 실제로 이벤트가 발생한 횟수보다 kubernetes-event-exporter 에 남는 로그 수가 더 적다. 쿠버네티스는 동일한 이벤트가 근접한 시간에 여러번 발생하면 기존에 etcd에 저장된 이벤트를 업데이트하는데 아마도 kubernetes-event-exporter가 이벤트가 새로 etcd에 생성되는 경우에만 로그를 남기기 때문인 것 같다.
comments powered by Disqus