Quellcode durchsuchen

service logs: Support no-follow mode

Signed-off-by: Andrea Luzzardi <aluzzardi@gmail.com>
Andrea Luzzardi vor 8 Jahren
Ursprung
Commit
c2d435e4f0

+ 0 - 4
api/server/router/swarm/cluster_routes.go

@@ -237,10 +237,6 @@ func (sr *swarmRouter) getServiceLogs(ctx context.Context, w http.ResponseWriter
 		OutStream: w,
 	}
 
-	if !logsConfig.Follow {
-		return fmt.Errorf("Bad parameters: Only follow mode is currently supported")
-	}
-
 	if logsConfig.Details {
 		return fmt.Errorf("Bad parameters: details is not currently supported")
 	}

+ 1 - 1
daemon/cluster/cluster.go

@@ -1275,7 +1275,7 @@ func (c *Cluster) ServiceLogs(ctx context.Context, input string, config *backend
 			ServiceIDs: []string{service.ID},
 		},
 		Options: &swarmapi.LogSubscriptionOptions{
-			Follow: true,
+			Follow: config.Follow,
 		},
 	})
 	if err != nil {

+ 5 - 1
daemon/cluster/executor/container/adapter.go

@@ -419,7 +419,11 @@ func (c *containerAdapter) logs(ctx context.Context, options api.LogSubscription
 	}
 
 	chStarted := make(chan struct{})
-	go c.backend.ContainerLogs(ctx, c.container.name(), apiOptions, chStarted)
+	go func() {
+		defer writer.Close()
+		c.backend.ContainerLogs(ctx, c.container.name(), apiOptions, chStarted)
+	}()
+
 	return reader, nil
 }
 

+ 38 - 7
integration-cli/docker_cli_service_logs_experimental_test.go

@@ -4,6 +4,7 @@ package main
 
 import (
 	"bufio"
+	"fmt"
 	"io"
 	"os/exec"
 	"strings"
@@ -24,7 +25,27 @@ func (s *DockerSwarmSuite) TestServiceLogs(c *check.C) {
 
 	name := "TestServiceLogs"
 
-	out, err := d.Cmd("service", "create", "--name", name, "busybox", "sh", "-c", "while true; do echo log test; sleep 1; done")
+	out, err := d.Cmd("service", "create", "--name", name, "--restart-condition", "none", "busybox", "sh", "-c", "echo hello world")
+	c.Assert(err, checker.IsNil)
+	c.Assert(strings.TrimSpace(out), checker.Not(checker.Equals), "")
+
+	// make sure task has been deployed.
+	waitAndAssert(c, defaultReconciliationTimeout, d.checkActiveContainerCount, checker.Equals, 1)
+
+	out, err = d.Cmd("service", "logs", name)
+	fmt.Println(out)
+	c.Assert(err, checker.IsNil)
+	c.Assert(out, checker.Contains, "hello world")
+}
+
+func (s *DockerSwarmSuite) TestServiceLogsFollow(c *check.C) {
+	testRequires(c, ExperimentalDaemon)
+
+	d := s.AddDaemon(c, true, true)
+
+	name := "TestServiceLogsFollow"
+
+	out, err := d.Cmd("service", "create", "--name", name, "busybox", "sh", "-c", "while true; do echo log test; sleep 0.1; done")
 	c.Assert(err, checker.IsNil)
 	c.Assert(strings.TrimSpace(out), checker.Not(checker.Equals), "")
 
@@ -40,16 +61,26 @@ func (s *DockerSwarmSuite) TestServiceLogs(c *check.C) {
 
 	// Make sure pipe is written to
 	ch := make(chan *logMessage)
+	done := make(chan struct{})
 	go func() {
 		reader := bufio.NewReader(r)
-		msg := &logMessage{}
-		msg.data, _, msg.err = reader.ReadLine()
-		ch <- msg
+		for {
+			msg := &logMessage{}
+			msg.data, _, msg.err = reader.ReadLine()
+			select {
+			case ch <- msg:
+			case <-done:
+				return
+			}
+		}
 	}()
 
-	msg := <-ch
-	c.Assert(msg.err, checker.IsNil)
-	c.Assert(string(msg.data), checker.Contains, "log test")
+	for i := 0; i < 3; i++ {
+		msg := <-ch
+		c.Assert(msg.err, checker.IsNil)
+		c.Assert(string(msg.data), checker.Contains, "log test")
+	}
+	close(done)
 
 	c.Assert(cmd.Process.Kill(), checker.IsNil)
 }