mirror of https://github.com/docker/docs.git
update docker info
add test Signed-off-by: Victor Vieux <vieux@docker.com>
This commit is contained in:
parent
5e3affa677
commit
f3a1027bbe
|
@ -29,23 +29,45 @@ const APIVERSION = "1.21"
|
||||||
|
|
||||||
// GET /info
|
// GET /info
|
||||||
func getInfo(c *context, w http.ResponseWriter, r *http.Request) {
|
func getInfo(c *context, w http.ResponseWriter, r *http.Request) {
|
||||||
info := dockerclient.Info{
|
info := apitypes.Info{
|
||||||
Containers: int64(len(c.cluster.Containers())),
|
Images: len(c.cluster.Images().Filter(cluster.ImageFilterOptions{})),
|
||||||
Images: int64(len(c.cluster.Images().Filter(cluster.ImageFilterOptions{}))),
|
|
||||||
DriverStatus: c.statusHandler.Status(),
|
DriverStatus: c.statusHandler.Status(),
|
||||||
NEventsListener: int64(c.eventsHandler.Size()),
|
NEventsListener: c.eventsHandler.Size(),
|
||||||
Debug: c.debug,
|
Debug: c.debug,
|
||||||
MemoryLimit: true,
|
MemoryLimit: true,
|
||||||
SwapLimit: true,
|
SwapLimit: true,
|
||||||
|
CPUCfsPeriod: true,
|
||||||
|
CPUCfsQuota: true,
|
||||||
|
CPUShares: true,
|
||||||
|
CPUSet: true,
|
||||||
IPv4Forwarding: true,
|
IPv4Forwarding: true,
|
||||||
BridgeNfIptables: true,
|
BridgeNfIptables: true,
|
||||||
BridgeNfIp6tables: true,
|
BridgeNfIP6tables: true,
|
||||||
NCPU: c.cluster.TotalCpus(),
|
OomKillDisable: true,
|
||||||
|
OperatingSystem: runtime.GOOS,
|
||||||
|
Architecture: runtime.GOARCH,
|
||||||
|
NCPU: int(c.cluster.TotalCpus()),
|
||||||
MemTotal: c.cluster.TotalMemory(),
|
MemTotal: c.cluster.TotalMemory(),
|
||||||
HttpProxy: os.Getenv("http_proxy"),
|
HTTPProxy: os.Getenv("http_proxy"),
|
||||||
HttpsProxy: os.Getenv("https_proxy"),
|
HTTPSProxy: os.Getenv("https_proxy"),
|
||||||
NoProxy: os.Getenv("no_proxy"),
|
NoProxy: os.Getenv("no_proxy"),
|
||||||
SystemTime: time.Now().Format(time.RFC3339Nano),
|
SystemTime: time.Now().Format(time.RFC3339Nano),
|
||||||
|
ExperimentalBuild: experimental.ENABLED,
|
||||||
|
}
|
||||||
|
|
||||||
|
if kernelVersion, err := kernel.GetKernelVersion(); err == nil {
|
||||||
|
info.KernelVersion = kernelVersion.String()
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, c := range c.cluster.Containers() {
|
||||||
|
info.Containers++
|
||||||
|
if c.Info.State.Paused {
|
||||||
|
info.ContainersPaused++
|
||||||
|
} else if c.Info.State.Running {
|
||||||
|
info.ContainersRunning++
|
||||||
|
} else {
|
||||||
|
info.ContainersStopped++
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if hostname, err := os.Hostname(); err == nil {
|
if hostname, err := os.Hostname(); err == nil {
|
||||||
|
|
|
@ -3,5 +3,5 @@ package api
|
||||||
// StatusHandler allows the API to display extra information on docker info.
|
// StatusHandler allows the API to display extra information on docker info.
|
||||||
type StatusHandler interface {
|
type StatusHandler interface {
|
||||||
// Info provides key/values to be added to docker info.
|
// Info provides key/values to be added to docker info.
|
||||||
Status() [][]string
|
Status() [][2]string
|
||||||
}
|
}
|
||||||
|
|
|
@ -49,16 +49,16 @@ type statusHandler struct {
|
||||||
follower *leadership.Follower
|
follower *leadership.Follower
|
||||||
}
|
}
|
||||||
|
|
||||||
func (h *statusHandler) Status() [][]string {
|
func (h *statusHandler) Status() [][2]string {
|
||||||
var status [][]string
|
var status [][2]string
|
||||||
|
|
||||||
if h.candidate != nil && !h.candidate.IsLeader() {
|
if h.candidate != nil && !h.candidate.IsLeader() {
|
||||||
status = [][]string{
|
status = [][2]string{
|
||||||
{"\bRole", "replica"},
|
{"\bRole", "replica"},
|
||||||
{"\bPrimary", h.follower.Leader()},
|
{"\bPrimary", h.follower.Leader()},
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
status = [][]string{
|
status = [][2]string{
|
||||||
{"\bRole", "primary"},
|
{"\bRole", "primary"},
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -69,7 +69,7 @@ type Cluster interface {
|
||||||
|
|
||||||
// Return some info about the cluster, like nb or containers / images
|
// Return some info about the cluster, like nb or containers / images
|
||||||
// It is pretty open, so the implementation decides what to return.
|
// It is pretty open, so the implementation decides what to return.
|
||||||
Info() [][]string
|
Info() [][2]string
|
||||||
|
|
||||||
// Return the total memory of the cluster
|
// Return the total memory of the cluster
|
||||||
TotalMemory() int64
|
TotalMemory() int64
|
||||||
|
|
|
@ -396,9 +396,9 @@ func (c *Cluster) TotalCpus() int64 {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Info gives minimal information about containers and resources on the mesos cluster
|
// Info gives minimal information about containers and resources on the mesos cluster
|
||||||
func (c *Cluster) Info() [][]string {
|
func (c *Cluster) Info() [][2]string {
|
||||||
offers := c.listOffers()
|
offers := c.listOffers()
|
||||||
info := [][]string{
|
info := [][2]string{
|
||||||
{"\bStrategy", c.scheduler.Strategy()},
|
{"\bStrategy", c.scheduler.Strategy()},
|
||||||
{"\bFilters", c.scheduler.Filters()},
|
{"\bFilters", c.scheduler.Filters()},
|
||||||
{"\bOffers", fmt.Sprintf("%d", len(offers))},
|
{"\bOffers", fmt.Sprintf("%d", len(offers))},
|
||||||
|
@ -407,9 +407,9 @@ func (c *Cluster) Info() [][]string {
|
||||||
sort.Sort(offerSorter(offers))
|
sort.Sort(offerSorter(offers))
|
||||||
|
|
||||||
for _, offer := range offers {
|
for _, offer := range offers {
|
||||||
info = append(info, []string{" Offer", offer.Id.GetValue()})
|
info = append(info, [2]string{" Offer", offer.Id.GetValue()})
|
||||||
for _, resource := range offer.Resources {
|
for _, resource := range offer.Resources {
|
||||||
info = append(info, []string{" └ " + resource.GetName(), formatResource(resource)})
|
info = append(info, [2]string{" └ " + resource.GetName(), formatResource(resource)})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -821,8 +821,8 @@ func (c *Cluster) TotalCpus() int64 {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Info returns some info about the cluster, like nb or containers / images
|
// Info returns some info about the cluster, like nb or containers / images
|
||||||
func (c *Cluster) Info() [][]string {
|
func (c *Cluster) Info() [][2]string {
|
||||||
info := [][]string{
|
info := [][2]string{
|
||||||
{"\bStrategy", c.scheduler.Strategy()},
|
{"\bStrategy", c.scheduler.Strategy()},
|
||||||
{"\bFilters", c.scheduler.Filters()},
|
{"\bFilters", c.scheduler.Filters()},
|
||||||
{"\bNodes", fmt.Sprintf("%d", len(c.engines)+len(c.pendingEngines))},
|
{"\bNodes", fmt.Sprintf("%d", len(c.engines)+len(c.pendingEngines))},
|
||||||
|
@ -832,23 +832,23 @@ func (c *Cluster) Info() [][]string {
|
||||||
sort.Sort(cluster.EngineSorter(engines))
|
sort.Sort(cluster.EngineSorter(engines))
|
||||||
|
|
||||||
for _, engine := range engines {
|
for _, engine := range engines {
|
||||||
info = append(info, []string{engine.Name, engine.Addr})
|
info = append(info, [2]string{engine.Name, engine.Addr})
|
||||||
info = append(info, []string{" └ Status", engine.Status()})
|
info = append(info, [2]string{" └ Status", engine.Status()})
|
||||||
info = append(info, []string{" └ Containers", fmt.Sprintf("%d", len(engine.Containers()))})
|
info = append(info, [2]string{" └ Containers", fmt.Sprintf("%d", len(engine.Containers()))})
|
||||||
info = append(info, []string{" └ Reserved CPUs", fmt.Sprintf("%d / %d", engine.UsedCpus(), engine.TotalCpus())})
|
info = append(info, [2]string{" └ Reserved CPUs", fmt.Sprintf("%d / %d", engine.UsedCpus(), engine.TotalCpus())})
|
||||||
info = append(info, []string{" └ Reserved Memory", fmt.Sprintf("%s / %s", units.BytesSize(float64(engine.UsedMemory())), units.BytesSize(float64(engine.TotalMemory())))})
|
info = append(info, [2]string{" └ Reserved Memory", fmt.Sprintf("%s / %s", units.BytesSize(float64(engine.UsedMemory())), units.BytesSize(float64(engine.TotalMemory())))})
|
||||||
labels := make([]string, 0, len(engine.Labels))
|
labels := make([]string, 0, len(engine.Labels))
|
||||||
for k, v := range engine.Labels {
|
for k, v := range engine.Labels {
|
||||||
labels = append(labels, k+"="+v)
|
labels = append(labels, k+"="+v)
|
||||||
}
|
}
|
||||||
sort.Strings(labels)
|
sort.Strings(labels)
|
||||||
info = append(info, []string{" └ Labels", fmt.Sprintf("%s", strings.Join(labels, ", "))})
|
info = append(info, [2]string{" └ Labels", fmt.Sprintf("%s", strings.Join(labels, ", "))})
|
||||||
errMsg := engine.ErrMsg()
|
errMsg := engine.ErrMsg()
|
||||||
if len(errMsg) == 0 {
|
if len(errMsg) == 0 {
|
||||||
errMsg = "(none)"
|
errMsg = "(none)"
|
||||||
}
|
}
|
||||||
info = append(info, []string{" └ Error", errMsg})
|
info = append(info, [2]string{" └ Error", errMsg})
|
||||||
info = append(info, []string{" └ UpdatedAt", engine.UpdatedAt().UTC().Format(time.RFC3339)})
|
info = append(info, [2]string{" └ UpdatedAt", engine.UpdatedAt().UTC().Format(time.RFC3339)})
|
||||||
}
|
}
|
||||||
|
|
||||||
return info
|
return info
|
||||||
|
|
|
@ -14,4 +14,32 @@ function teardown() {
|
||||||
[ "$status" -eq 0 ]
|
[ "$status" -eq 0 ]
|
||||||
[[ "${output}" == *"Nodes: 2"* ]]
|
[[ "${output}" == *"Nodes: 2"* ]]
|
||||||
[[ "${output}" == *"└ Labels:"*"foo=bar"* ]]
|
[[ "${output}" == *"└ Labels:"*"foo=bar"* ]]
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@test "docker info - details" {
|
||||||
|
# details in docker info were introduced in docker 1.10, skip older version without
|
||||||
|
run docker info
|
||||||
|
if [[ "${output}" != *"Paused:"* ]]; then
|
||||||
|
skip
|
||||||
|
fi
|
||||||
|
|
||||||
|
start_docker_with_busybox 2
|
||||||
|
swarm_manage
|
||||||
|
|
||||||
|
docker_swarm run -d --name test busybox sleep 100
|
||||||
|
run docker_swarm info
|
||||||
|
[ "$status" -eq 0 ]
|
||||||
|
[[ "${output}" == *"Running: 1"* ]]
|
||||||
|
|
||||||
|
docker_swarm pause test
|
||||||
|
run docker_swarm info
|
||||||
|
[ "$status" -eq 0 ]
|
||||||
|
[[ "${output}" == *"Paused: 1"* ]]
|
||||||
|
|
||||||
|
docker_swarm unpause test
|
||||||
|
docker_swarm kill test
|
||||||
|
run docker_swarm info
|
||||||
|
[ "$status" -eq 0 ]
|
||||||
|
[[ "${output}" == *"Stopped: 1"* ]]
|
||||||
|
}
|
Loading…
Reference in New Issue