summaryrefslogtreecommitdiff
path: root/daemon/attach.go
diff options
context:
space:
mode:
authorDavid Calavera <david.calavera@gmail.com>2015-11-03 12:33:13 -0500
committerDavid Calavera <david.calavera@gmail.com>2015-11-04 12:27:48 -0500
commitca5ede2d0a23cb84cac3b863c363d0269e6438df (patch)
tree401deee3f41f901c3c42e8cdd7a9985e6bc25ce3 /daemon/attach.go
parent2c72015ce3b78b45e33529368fb1c5a724415d87 (diff)
downloaddocker-ca5ede2d0a23cb84cac3b863c363d0269e6438df.tar.gz
Decouple daemon and container to log events.
Create a supervisor interface to let the container monitor to emit events. Signed-off-by: David Calavera <david.calavera@gmail.com>
Diffstat (limited to 'daemon/attach.go')
-rw-r--r--daemon/attach.go63
1 files changed, 61 insertions, 2 deletions
diff --git a/daemon/attach.go b/daemon/attach.go
index 44198788ce..64a1223a4d 100644
--- a/daemon/attach.go
+++ b/daemon/attach.go
@@ -2,7 +2,10 @@ package daemon
import (
"io"
+ "time"
+ "github.com/Sirupsen/logrus"
+ "github.com/docker/docker/daemon/logger"
"github.com/docker/docker/pkg/stdcopy"
)
@@ -43,7 +46,7 @@ func (daemon *Daemon) ContainerAttachWithLogs(prefixOrName string, c *ContainerA
stderr = errStream
}
- return container.attachWithLogs(stdin, stdout, stderr, c.Logs, c.Stream)
+ return daemon.attachWithLogs(container, stdin, stdout, stderr, c.Logs, c.Stream)
}
// ContainerWsAttachWithLogsConfig attach with websockets, since all
@@ -60,5 +63,61 @@ func (daemon *Daemon) ContainerWsAttachWithLogs(prefixOrName string, c *Containe
if err != nil {
return err
}
- return container.attachWithLogs(c.InStream, c.OutStream, c.ErrStream, c.Logs, c.Stream)
+ return daemon.attachWithLogs(container, c.InStream, c.OutStream, c.ErrStream, c.Logs, c.Stream)
+}
+
+func (daemon *Daemon) attachWithLogs(container *Container, stdin io.ReadCloser, stdout, stderr io.Writer, logs, stream bool) error {
+ if logs {
+ logDriver, err := container.getLogger()
+ if err != nil {
+ return err
+ }
+ cLog, ok := logDriver.(logger.LogReader)
+ if !ok {
+ return logger.ErrReadLogsNotSupported
+ }
+ logs := cLog.ReadLogs(logger.ReadConfig{Tail: -1})
+
+ LogLoop:
+ for {
+ select {
+ case msg, ok := <-logs.Msg:
+ if !ok {
+ break LogLoop
+ }
+ if msg.Source == "stdout" && stdout != nil {
+ stdout.Write(msg.Line)
+ }
+ if msg.Source == "stderr" && stderr != nil {
+ stderr.Write(msg.Line)
+ }
+ case err := <-logs.Err:
+ logrus.Errorf("Error streaming logs: %v", err)
+ break LogLoop
+ }
+ }
+ }
+
+ daemon.LogContainerEvent(container, "attach")
+
+ //stream
+ if stream {
+ var stdinPipe io.ReadCloser
+ if stdin != nil {
+ r, w := io.Pipe()
+ go func() {
+ defer w.Close()
+ defer logrus.Debugf("Closing buffered stdin pipe")
+ io.Copy(w, stdin)
+ }()
+ stdinPipe = r
+ }
+ <-container.Attach(stdinPipe, stdout, stderr)
+ // If we are in stdinonce mode, wait for the process to end
+ // otherwise, simply return
+ if container.Config.StdinOnce && !container.Config.Tty {
+ container.WaitStop(-1 * time.Second)
+ }
+ }
+ return nil
}