From c9783fac610652a848a89de478a74d1924ab50d0 Mon Sep 17 00:00:00 2001 From: Raul Cabello Martin Date: Wed, 26 May 2021 23:33:03 +0200 Subject: [PATCH] =?UTF-8?q?feat(log):=20Support=20of=20kubectl.kubernetes.?= =?UTF-8?q?io/default-logs-container=20an=E2=80=A6=20(#1133)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * feat(log): Support of kubectl.kubernetes.io/default-logs-container annotation Closes #1057 * feat(log): Support of kubectl.kubernetes.io/default-logs-container annotation refactored to return ok bool with the container Closes #1057 * feat(log): Support of kubectl.kubernetes.io/default-logs-container annotation refactored getDefaultLogContainer log if container was not found --- internal/dao/pod.go | 26 ++++++++++++++++++++++-- internal/dao/pod_test.go | 44 ++++++++++++++++++++++++++++++++++++++++ 2 files changed, 68 insertions(+), 2 deletions(-) create mode 100644 internal/dao/pod_test.go diff --git a/internal/dao/pod.go b/internal/dao/pod.go index 1de4ed59..b1942e05 100644 --- a/internal/dao/pod.go +++ b/internal/dao/pod.go @@ -32,8 +32,9 @@ var ( ) const ( - logRetryCount = 20 - logRetryWait = 1 * time.Second + logRetryCount = 20 + logRetryWait = 1 * time.Second + defaultLogContainerAnnotation = "kubectl.kubernetes.io/default-logs-container" ) // Pod represents a pod resource. @@ -195,6 +196,13 @@ func (p *Pod) TailLogs(ctx context.Context, c LogChan, opts LogOptions) error { opts.SingleContainer = true return tailLogs(ctx, p, c, opts) } + + if defaultContainer, ok := getDefaultLogContainer(po); ok { + opts.SingleContainer = true + opts.Container = defaultContainer + return tailLogs(ctx, p, c, opts) + } + if len(po.Spec.InitContainers)+len(po.Spec.Containers) == 1 { opts.SingleContainer = true } @@ -491,3 +499,17 @@ func (p *Pod) isControlled(path string) (string, bool, error) { } return "", false, nil } + +func getDefaultLogContainer(po v1.Pod) (string, bool) { + defaultContainer, ok := po.GetAnnotations()[defaultLogContainerAnnotation] + if ok { + for _, container := range po.Spec.Containers { + if container.Name == defaultContainer { + return defaultContainer, true + } + } + log.Warn().Msg(defaultContainer + " container not found. " + defaultLogContainerAnnotation + " annotation will be ignored") + } + + return "", false +} diff --git a/internal/dao/pod_test.go b/internal/dao/pod_test.go new file mode 100644 index 00000000..a340dbfd --- /dev/null +++ b/internal/dao/pod_test.go @@ -0,0 +1,44 @@ +package dao + +import ( + "testing" + + "github.com/stretchr/testify/assert" + v1 "k8s.io/api/core/v1" + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" +) + +func TestGetDefaultLogContainer(t *testing.T) { + type args struct { + imageSpecs ImageSpecs + } + uu := map[string]struct { + po v1.Pod + wantContainer string + wantOk bool + }{ + "no_annotation": { + po: v1.Pod{}, + wantContainer: "", + wantOk: false, + }, + "container_not_present": { + po: v1.Pod{ObjectMeta: metav1.ObjectMeta{Annotations: map[string]string{"kubectl.kubernetes.io/default-logs-container": "container1"}}}, + wantContainer: "", + wantOk: false, + }, + "container_found": { + po: v1.Pod{ObjectMeta: metav1.ObjectMeta{Annotations: map[string]string{"kubectl.kubernetes.io/default-logs-container": "container1"}}, Spec: v1.PodSpec{Containers: []v1.Container{{Name: "container1"}}}}, + wantContainer: "container1", + wantOk: true, + }, + } + for k := range uu { + u := uu[k] + t.Run(k, func(t *testing.T) { + container, ok := getDefaultLogContainer(u.po) + assert.Equal(t, u.wantContainer, container) + assert.Equal(t, u.wantOk, ok) + }) + } +}