...
1
2
3
4
5
6
7
8
9
10
11
12
13
14 package collector
15
16 import (
17 "context"
18
19 "github.com/pkg/errors"
20 corev1 "k8s.io/api/core/v1"
21 apierrors "k8s.io/apimachinery/pkg/api/errors"
22 "k8s.io/apimachinery/pkg/types"
23 "sigs.k8s.io/controller-runtime/pkg/client"
24 )
25
26 const ExitCode string = "exitCode"
27
28 type ExitCodeCollector struct {
29 kubeClient client.Client
30 namespace string
31 podName string
32 containerName string
33 }
34
35 func NewExitCodeCollector(kubeClient client.Client, namespace string, podName string, containerName string) *ExitCodeCollector {
36 return &ExitCodeCollector{kubeClient: kubeClient, namespace: namespace, podName: podName, containerName: containerName}
37 }
38
39 func (it *ExitCodeCollector) CollectContext(ctx context.Context) (env map[string]interface{}, err error) {
40 var pod corev1.Pod
41 err = it.kubeClient.Get(ctx, types.NamespacedName{
42 Namespace: it.namespace,
43 Name: it.podName,
44 }, &pod)
45
46 if apierrors.IsNotFound(err) {
47 return nil, nil
48 }
49
50 if err != nil {
51 return nil, err
52 }
53
54 var targetContainerStatus corev1.ContainerStatus
55 found := false
56 for _, containerStatus := range pod.Status.ContainerStatuses {
57 if containerStatus.Name == it.containerName {
58 targetContainerStatus = containerStatus
59 found = true
60 break
61 }
62 }
63
64 if !found {
65 return nil, errors.Errorf("no such contaienr called %s in pod %s/%s", it.containerName, pod.Namespace, pod.Name)
66 }
67
68 if targetContainerStatus.State.Terminated == nil {
69 return nil, errors.Errorf("container %s in pod %s/%s is waiting or running, not in ternimated", it.containerName, pod.Namespace, pod.Name)
70 }
71
72 return map[string]interface{}{
73 ExitCode: targetContainerStatus.State.Terminated.ExitCode,
74 }, nil
75 }
76