diff --git a/README.md b/README.md index 0533719..d2ece74 100644 --- a/README.md +++ b/README.md @@ -13,7 +13,6 @@ Add a process: ```bash curl -s -XPUT localhost:8888/containers/redis/process -d@process.json | json_pp { - "pid" : 25671, "user" : { "gid" : 0, "uid" : 0 @@ -31,10 +30,10 @@ curl -s -XPUT localhost:8888/containers/redis/process -d@process.json | json_pp ``` -Get containers: +Get containers and state: ```bash -curl -s localhost:8888/containers | json_pp +curl -s localhost:8888/state | json_pp { "containers" : [ { diff --git a/api/v1/server.go b/api/v1/server.go index 47a7e30..16847e7 100644 --- a/api/v1/server.go +++ b/api/v1/server.go @@ -30,7 +30,7 @@ func NewServer(supervisor *containerd.Supervisor) http.Handler { // internal method for replaying the journal r.HandleFunc("/event", s.event).Methods("POST") r.HandleFunc("/events", s.events).Methods("GET") - r.HandleFunc("/containers", s.containers).Methods("GET") + r.HandleFunc("/state", s.state).Methods("GET") return s } @@ -100,7 +100,7 @@ func (s *server) event(w http.ResponseWriter, r *http.Request) { return } if e.Containers != nil && len(e.Containers) > 0 { - if err := writeContainers(w, &e); err != nil { + if err := s.writeState(w, &e); err != nil { http.Error(w, err.Error(), http.StatusInternalServerError) return } @@ -170,22 +170,28 @@ func (s *server) signalPid(w http.ResponseWriter, r *http.Request) { } } -func (s *server) containers(w http.ResponseWriter, r *http.Request) { +func (s *server) state(w http.ResponseWriter, r *http.Request) { e := containerd.NewEvent(containerd.GetContainerEventType) s.supervisor.SendEvent(e) if err := <-e.Err; err != nil { http.Error(w, err.Error(), http.StatusInternalServerError) return } - if err := writeContainers(w, e); err != nil { + if err := s.writeState(w, e); err != nil { http.Error(w, err.Error(), http.StatusInternalServerError) return } } -func writeContainers(w http.ResponseWriter, e *containerd.Event) error { - var state State - state.Containers = []Container{} +func (s *server) writeState(w http.ResponseWriter, e *containerd.Event) error { + m := s.supervisor.Machine() + state := State{ + Containers: []Container{}, + Machine: Machine{ + Cpus: m.Cpus, + Memory: m.Memory, + }, + } for _, c := range e.Containers { processes, err := c.Processes() if err != nil { diff --git a/api/v1/types.go b/api/v1/types.go index e32addf..cbf543d 100644 --- a/api/v1/types.go +++ b/api/v1/types.go @@ -2,6 +2,7 @@ package v1 type State struct { Containers []Container `json:"containers"` + Machine Machine `json:"machine"` } type Status string @@ -11,6 +12,11 @@ const ( Running Status = "running" ) +type Machine struct { + Cpus int `json:"cpus"` + Memory int64 `json:"memory"` +} + type ContainerState struct { Status Status `json:"status,omitempty"` } diff --git a/machine.go b/machine.go new file mode 100644 index 0000000..746d827 --- /dev/null +++ b/machine.go @@ -0,0 +1,23 @@ +package containerd + +import "github.com/cloudfoundry/gosigar" + +type Machine struct { + Cpus int + Memory int64 +} + +func CollectMachineInformation() (Machine, error) { + m := Machine{} + cpu := sigar.CpuList{} + if err := cpu.Get(); err != nil { + return m, err + } + m.Cpus = len(cpu.List) + mem := sigar.Mem{} + if err := mem.Get(); err != nil { + return m, err + } + m.Memory = int64(mem.Total) + return m, nil +} diff --git a/supervisor.go b/supervisor.go index 30a053b..4e4a153 100644 --- a/supervisor.go +++ b/supervisor.go @@ -24,6 +24,10 @@ func NewSupervisor(stateDir string, tasks chan *StartTask) (*Supervisor, error) if err != nil { return nil, err } + machine, err := CollectMachineInformation() + if err != nil { + return nil, err + } s := &Supervisor{ stateDir: stateDir, containers: make(map[string]runtime.Container), @@ -32,6 +36,7 @@ func NewSupervisor(stateDir string, tasks chan *StartTask) (*Supervisor, error) journal: j, tasks: tasks, events: make(chan *Event, 2048), + machine: machine, } // register default event handlers s.handlers = map[EventType]Handler{ @@ -59,6 +64,7 @@ type Supervisor struct { events chan *Event tasks chan *StartTask subscribers map[subscriber]bool + machine Machine } type subscriber chan *Event @@ -114,6 +120,12 @@ func (s *Supervisor) Start() error { return nil } +// Machine returns the machine information for which the +// supervisor is executing on. +func (s *Supervisor) Machine() Machine { + return s.machine +} + func (s *Supervisor) getContainerForPid(pid int) (runtime.Container, error) { for _, container := range s.containers { cpid, err := container.Pid()