diff --git a/api/common.go b/api/common.go index fd065d5abe..cde250ff93 100644 --- a/api/common.go +++ b/api/common.go @@ -21,7 +21,7 @@ import ( // Common constants for daemon and client. const ( // DefaultVersion of Current REST API - DefaultVersion string = "1.26" + DefaultVersion string = "1.27" // NoBaseImageSpecifier is the symbol used by the FROM // command to specify that no base image is to be used. diff --git a/api/swagger.yaml b/api/swagger.yaml index 4399dd688a..8ebc72aa52 100644 --- a/api/swagger.yaml +++ b/api/swagger.yaml @@ -19,10 +19,10 @@ produces: consumes: - "application/json" - "text/plain" -basePath: "/v1.26" +basePath: "/v1.27" info: title: "Docker Engine API" - version: "1.26" + version: "1.27" x-logo: url: "https://docs.docker.com/images/logo-docker-main.png" description: | @@ -44,7 +44,7 @@ info: The API is usually changed in each release of Docker, so API calls are versioned to ensure that clients don't break. - For Docker Engine >= 1.13.1, the API version is 1.26. To lock to this version, you prefix the URL with `/v1.26`. For example, calling `/info` is the same as calling `/v1.26/info`. + For Docker Engine >= 17.03.1, the API version is 1.27. To lock to this version, you prefix the URL with `/v1.27`. For example, calling `/info` is the same as calling `/v1.27/info`. Engine releases in the near future should support this version of the API, so your client will continue to work even if it is talking to a newer Engine. @@ -52,10 +52,11 @@ info: The API uses an open schema model, which means server may add extra properties to responses. Likewise, the server will ignore any extra query parameters and request body properties. When you write clients, you need to ignore additional properties in responses to ensure they do not break when talking to newer Docker daemons. - This documentation is for version 1.26 of the API, which was introduced with Docker 1.13.1. Use this table to find documentation for previous versions of the API: + This documentation is for version 1.27 of the API, which was introduced with Docker 17.03.1. Use this table to find documentation for previous versions of the API: Docker version | API version | Changes ----------------|-------------|--------- + 1.13.1 & 17.03.0 | [1.26](https://docs.docker.com/engine/api/v1.26/) | [API changes](https://docs.docker.com/engine/api/version-history/#v1-26-api-changes) 1.13.0 | [1.25](https://docs.docker.com/engine/api/v1.25/) | [API changes](https://docs.docker.com/engine/api/version-history/#v1-25-api-changes) 1.12.x | [1.24](https://docs.docker.com/engine/api/v1.24/) | [API changes](https://docs.docker.com/engine/api/version-history/#v1-24-api-changes) 1.11.x | [1.23](https://docs.docker.com/engine/api/v1.23/) | [API changes](https://docs.docker.com/engine/api/version-history/#v1-23-api-changes) @@ -3378,7 +3379,13 @@ paths: description: | This endpoint returns a live stream of a container’s resource usage statistics. - The `precpu_stats` is the CPU statistic of last read, which is used for calculating the CPU usage percentage. It is not the same as the `cpu_stats` field. + The `precpu_stats` is the CPU statistic of last read, which is used + for calculating the CPU usage percentage. It is not the same as the + `cpu_stats` field. + + If either `precpu_stats.online_cpus` or `cpu_stats.online_cpus` is + nil then for compatibility with older daemons the length of the + corresponding `cpu_usage.percpu_usage` array should be used. operationId: "ContainerStats" produces: - "application/json" @@ -3458,6 +3465,7 @@ paths: total_usage: 100215355 usage_in_kernelmode: 30000000 system_cpu_usage: 739306590000000 + online_cpus: 4 throttling_data: periods: 0 throttled_periods: 0 @@ -3473,6 +3481,7 @@ paths: total_usage: 100093996 usage_in_kernelmode: 30000000 system_cpu_usage: 9492140000000 + online_cpus: 4 throttling_data: periods: 0 throttled_periods: 0 diff --git a/api/types/stats.go b/api/types/stats.go index 9bf1928b8c..7ca76a5b63 100644 --- a/api/types/stats.go +++ b/api/types/stats.go @@ -47,6 +47,9 @@ type CPUStats struct { // System Usage. Linux only. SystemUsage uint64 `json:"system_cpu_usage,omitempty"` + // Online CPUs. Linux only. + OnlineCPUs uint32 `json:"online_cpus,omitempty"` + // Throttling Data. Linux only. ThrottlingData ThrottlingData `json:"throttling_data,omitempty"` } diff --git a/cli/command/container/stats_helpers.go b/cli/command/container/stats_helpers.go index 4b57e3fe05..b1a7740486 100644 --- a/cli/command/container/stats_helpers.go +++ b/cli/command/container/stats_helpers.go @@ -179,10 +179,14 @@ func calculateCPUPercentUnix(previousCPU, previousSystem uint64, v *types.StatsJ cpuDelta = float64(v.CPUStats.CPUUsage.TotalUsage) - float64(previousCPU) // calculate the change for the entire system between readings systemDelta = float64(v.CPUStats.SystemUsage) - float64(previousSystem) + onlineCPUs = float64(v.CPUStats.OnlineCPUs) ) + if onlineCPUs == 0.0 { + onlineCPUs = float64(len(v.CPUStats.CPUUsage.PercpuUsage)) + } if systemDelta > 0.0 && cpuDelta > 0.0 { - cpuPercent = (cpuDelta / systemDelta) * float64(len(v.CPUStats.CPUUsage.PercpuUsage)) * 100.0 + cpuPercent = (cpuDelta / systemDelta) * onlineCPUs * 100.0 } return cpuPercent } diff --git a/client/client.go b/client/client.go index c3e85d455a..50f9fe119d 100644 --- a/client/client.go +++ b/client/client.go @@ -58,7 +58,7 @@ import ( ) // DefaultVersion is the version of the current stable API -const DefaultVersion string = "1.26" +const DefaultVersion string = "1.27" // Client is the API client that performs all operations // against a docker server. diff --git a/daemon/stats_collector.go b/daemon/stats_collector.go index 291933b7ac..6b2bf1a65d 100644 --- a/daemon/stats_collector.go +++ b/daemon/stats_collector.go @@ -115,6 +115,12 @@ func (s *statsCollector) run() { continue } + onlineCPUs, err := s.getNumberOnlineCPUs() + if err != nil { + logrus.Errorf("collecting system online cpu count: %v", err) + continue + } + for _, pair := range pairs { stats, err := s.supervisor.GetContainerStats(pair.container) if err != nil { @@ -132,6 +138,7 @@ func (s *statsCollector) run() { } // FIXME: move to containerd on Linux (not Windows) stats.CPUStats.SystemUsage = systemUsage + stats.CPUStats.OnlineCPUs = onlineCPUs pair.publisher.Publish(*stats) } diff --git a/daemon/stats_collector_unix.go b/daemon/stats_collector_unix.go index 0fcc9c5828..0a81cb8b68 100644 --- a/daemon/stats_collector_unix.go +++ b/daemon/stats_collector_unix.go @@ -12,6 +12,11 @@ import ( "github.com/opencontainers/runc/libcontainer/system" ) +/* +#include +*/ +import "C" + // platformNewStatsCollector performs platform specific initialisation of the // statsCollector structure. func platformNewStatsCollector(s *statsCollector) { @@ -69,3 +74,11 @@ func (s *statsCollector) getSystemCPUUsage() (uint64, error) { } return 0, fmt.Errorf("invalid stat format. Error trying to parse the '/proc/stat' file") } + +func (s *statsCollector) getNumberOnlineCPUs() (uint32, error) { + i, err := C.sysconf(C._SC_NPROCESSORS_ONLN) + if err != nil { + return 0, err + } + return uint32(i), nil +} diff --git a/daemon/stats_collector_windows.go b/daemon/stats_collector_windows.go index 41731b9c14..435bc4b59c 100644 --- a/daemon/stats_collector_windows.go +++ b/daemon/stats_collector_windows.go @@ -13,3 +13,7 @@ func platformNewStatsCollector(s *statsCollector) { func (s *statsCollector) getSystemCPUUsage() (uint64, error) { return 0, nil } + +func (s *statsCollector) getNumberOnlineCPUs() (uint32, error) { + return 0, nil +} diff --git a/docs/api/version-history.md b/docs/api/version-history.md index a9cd07c1f1..5f3a006264 100644 --- a/docs/api/version-history.md +++ b/docs/api/version-history.md @@ -13,6 +13,12 @@ keywords: "API, Docker, rcli, REST, documentation" will be rejected. --> +## v1.27 API changes + +[Docker Engine API v1.27](https://docs.docker.com/engine/api/v1.27/) documentation + +* `GET /containers/(id or name)/stats` now includes an `online_cpus` field in both `precpu_stats` and `cpu_stats`. If this field is `nil` then for compatibility with older daemons the length of the corresponding `cpu_usage.percpu_usage` array should be used. + ## v1.26 API changes [Docker Engine API v1.26](https://docs.docker.com/engine/api/v1.26/) documentation