github.com/sijibomii/docker@v0.0.0-20231230191044-5cf6ca554647/daemon/logger/copier_test.go (about)

     1  package logger
     2  
     3  import (
     4  	"bytes"
     5  	"encoding/json"
     6  	"io"
     7  	"testing"
     8  	"time"
     9  )
    10  
    11  type TestLoggerJSON struct {
    12  	*json.Encoder
    13  	delay time.Duration
    14  }
    15  
    16  func (l *TestLoggerJSON) Log(m *Message) error {
    17  	if l.delay > 0 {
    18  		time.Sleep(l.delay)
    19  	}
    20  	return l.Encode(m)
    21  }
    22  
    23  func (l *TestLoggerJSON) Close() error { return nil }
    24  
    25  func (l *TestLoggerJSON) Name() string { return "json" }
    26  
    27  type TestLoggerText struct {
    28  	*bytes.Buffer
    29  }
    30  
    31  func (l *TestLoggerText) Log(m *Message) error {
    32  	_, err := l.WriteString(m.ContainerID + " " + m.Source + " " + string(m.Line) + "\n")
    33  	return err
    34  }
    35  
    36  func (l *TestLoggerText) Close() error { return nil }
    37  
    38  func (l *TestLoggerText) Name() string { return "text" }
    39  
    40  func TestCopier(t *testing.T) {
    41  	stdoutLine := "Line that thinks that it is log line from docker stdout"
    42  	stderrLine := "Line that thinks that it is log line from docker stderr"
    43  	var stdout bytes.Buffer
    44  	var stderr bytes.Buffer
    45  	for i := 0; i < 30; i++ {
    46  		if _, err := stdout.WriteString(stdoutLine + "\n"); err != nil {
    47  			t.Fatal(err)
    48  		}
    49  		if _, err := stderr.WriteString(stderrLine + "\n"); err != nil {
    50  			t.Fatal(err)
    51  		}
    52  	}
    53  
    54  	var jsonBuf bytes.Buffer
    55  
    56  	jsonLog := &TestLoggerJSON{Encoder: json.NewEncoder(&jsonBuf)}
    57  
    58  	cid := "a7317399f3f857173c6179d44823594f8294678dea9999662e5c625b5a1c7657"
    59  	c := NewCopier(cid,
    60  		map[string]io.Reader{
    61  			"stdout": &stdout,
    62  			"stderr": &stderr,
    63  		},
    64  		jsonLog)
    65  	c.Run()
    66  	wait := make(chan struct{})
    67  	go func() {
    68  		c.Wait()
    69  		close(wait)
    70  	}()
    71  	select {
    72  	case <-time.After(1 * time.Second):
    73  		t.Fatal("Copier failed to do its work in 1 second")
    74  	case <-wait:
    75  	}
    76  	dec := json.NewDecoder(&jsonBuf)
    77  	for {
    78  		var msg Message
    79  		if err := dec.Decode(&msg); err != nil {
    80  			if err == io.EOF {
    81  				break
    82  			}
    83  			t.Fatal(err)
    84  		}
    85  		if msg.Source != "stdout" && msg.Source != "stderr" {
    86  			t.Fatalf("Wrong Source: %q, should be %q or %q", msg.Source, "stdout", "stderr")
    87  		}
    88  		if msg.ContainerID != cid {
    89  			t.Fatalf("Wrong ContainerID: %q, expected %q", msg.ContainerID, cid)
    90  		}
    91  		if msg.Source == "stdout" {
    92  			if string(msg.Line) != stdoutLine {
    93  				t.Fatalf("Wrong Line: %q, expected %q", msg.Line, stdoutLine)
    94  			}
    95  		}
    96  		if msg.Source == "stderr" {
    97  			if string(msg.Line) != stderrLine {
    98  				t.Fatalf("Wrong Line: %q, expected %q", msg.Line, stderrLine)
    99  			}
   100  		}
   101  	}
   102  }
   103  
   104  func TestCopierSlow(t *testing.T) {
   105  	stdoutLine := "Line that thinks that it is log line from docker stdout"
   106  	var stdout bytes.Buffer
   107  	for i := 0; i < 30; i++ {
   108  		if _, err := stdout.WriteString(stdoutLine + "\n"); err != nil {
   109  			t.Fatal(err)
   110  		}
   111  	}
   112  
   113  	var jsonBuf bytes.Buffer
   114  	//encoder := &encodeCloser{Encoder: json.NewEncoder(&jsonBuf)}
   115  	jsonLog := &TestLoggerJSON{Encoder: json.NewEncoder(&jsonBuf), delay: 100 * time.Millisecond}
   116  
   117  	cid := "a7317399f3f857173c6179d44823594f8294678dea9999662e5c625b5a1c7657"
   118  	c := NewCopier(cid, map[string]io.Reader{"stdout": &stdout}, jsonLog)
   119  	c.Run()
   120  	wait := make(chan struct{})
   121  	go func() {
   122  		c.Wait()
   123  		close(wait)
   124  	}()
   125  	<-time.After(150 * time.Millisecond)
   126  	c.Close()
   127  	select {
   128  	case <-time.After(200 * time.Millisecond):
   129  		t.Fatalf("failed to exit in time after the copier is closed")
   130  	case <-wait:
   131  	}
   132  }