diff --git a/daemon/daemon.go b/daemon/daemon.go index 6ff82253ab..815bacccd7 100644 --- a/daemon/daemon.go +++ b/daemon/daemon.go @@ -158,6 +158,9 @@ func (daemon *Daemon) Install(eng *engine.Engine) error { if err := eng.Register("container_changes", daemon.ContainerChanges); err != nil { return err } + if err := eng.Register("top", daemon.ContainerTop); err != nil { + return err + } return nil } diff --git a/daemon/top.go b/daemon/top.go new file mode 100644 index 0000000000..ceaeea157e --- /dev/null +++ b/daemon/top.go @@ -0,0 +1,79 @@ +package daemon + +import ( + "os/exec" + "strconv" + "strings" + + "github.com/docker/docker/engine" +) + +func (daemon *Daemon) ContainerTop(job *engine.Job) engine.Status { + if len(job.Args) != 1 && len(job.Args) != 2 { + return job.Errorf("Not enough arguments. Usage: %s CONTAINER [PS_ARGS]\n", job.Name) + } + var ( + name = job.Args[0] + psArgs = "-ef" + ) + + if len(job.Args) == 2 && job.Args[1] != "" { + psArgs = job.Args[1] + } + + if container := daemon.Get(name); container != nil { + if !container.State.IsRunning() { + return job.Errorf("Container %s is not running", name) + } + pids, err := daemon.ExecutionDriver().GetPidsForContainer(container.ID) + if err != nil { + return job.Error(err) + } + output, err := exec.Command("ps", psArgs).Output() + if err != nil { + return job.Errorf("Error running ps: %s", err) + } + + lines := strings.Split(string(output), "\n") + header := strings.Fields(lines[0]) + out := &engine.Env{} + out.SetList("Titles", header) + + pidIndex := -1 + for i, name := range header { + if name == "PID" { + pidIndex = i + } + } + if pidIndex == -1 { + return job.Errorf("Couldn't find PID field in ps output") + } + + processes := [][]string{} + for _, line := range lines[1:] { + if len(line) == 0 { + continue + } + fields := strings.Fields(line) + p, err := strconv.Atoi(fields[pidIndex]) + if err != nil { + return job.Errorf("Unexpected pid '%s': %s", fields[pidIndex], err) + } + + for _, pid := range pids { + if pid == p { + // Make sure number of fields equals number of header titles + // merging "overhanging" fields + process := fields[:len(header)-1] + process = append(process, strings.Join(fields[len(header)-1:], " ")) + processes = append(processes, process) + } + } + } + out.SetJson("Processes", processes) + out.WriteTo(job.Stdout) + return engine.StatusOK + + } + return job.Errorf("No such container: %s", name) +} diff --git a/server/container.go b/server/container.go index 2c8958e8f9..9ee77cf4d5 100644 --- a/server/container.go +++ b/server/container.go @@ -7,8 +7,6 @@ package server import ( "errors" "fmt" - "os/exec" - "strconv" "strings" "github.com/docker/docker/daemon" @@ -16,76 +14,6 @@ import ( "github.com/docker/docker/pkg/graphdb" ) -func (srv *Server) ContainerTop(job *engine.Job) engine.Status { - if len(job.Args) != 1 && len(job.Args) != 2 { - return job.Errorf("Not enough arguments. Usage: %s CONTAINER [PS_ARGS]\n", job.Name) - } - var ( - name = job.Args[0] - psArgs = "-ef" - ) - - if len(job.Args) == 2 && job.Args[1] != "" { - psArgs = job.Args[1] - } - - if container := srv.daemon.Get(name); container != nil { - if !container.State.IsRunning() { - return job.Errorf("Container %s is not running", name) - } - pids, err := srv.daemon.ExecutionDriver().GetPidsForContainer(container.ID) - if err != nil { - return job.Error(err) - } - output, err := exec.Command("ps", psArgs).Output() - if err != nil { - return job.Errorf("Error running ps: %s", err) - } - - lines := strings.Split(string(output), "\n") - header := strings.Fields(lines[0]) - out := &engine.Env{} - out.SetList("Titles", header) - - pidIndex := -1 - for i, name := range header { - if name == "PID" { - pidIndex = i - } - } - if pidIndex == -1 { - return job.Errorf("Couldn't find PID field in ps output") - } - - processes := [][]string{} - for _, line := range lines[1:] { - if len(line) == 0 { - continue - } - fields := strings.Fields(line) - p, err := strconv.Atoi(fields[pidIndex]) - if err != nil { - return job.Errorf("Unexpected pid '%s': %s", fields[pidIndex], err) - } - - for _, pid := range pids { - if pid == p { - // Make sure number of fields equals number of header titles - // merging "overhanging" fields - process := fields[:len(header)-1] - process = append(process, strings.Join(fields[len(header)-1:], " ")) - processes = append(processes, process) - } - } - } - out.SetJson("Processes", processes) - out.WriteTo(job.Stdout) - return engine.StatusOK - - } - return job.Errorf("No such container: %s", name) -} - func (srv *Server) Containers(job *engine.Job) engine.Status { var ( foundBefore bool diff --git a/server/init.go b/server/init.go index 77a52317ce..8a31a36379 100644 --- a/server/init.go +++ b/server/init.go @@ -93,7 +93,6 @@ func InitServer(job *engine.Job) engine.Status { "history": srv.ImageHistory, "viz": srv.ImagesViz, "log": srv.Log, - "top": srv.ContainerTop, "load": srv.ImageLoad, "build": srv.Build, "pull": srv.ImagePull,