From 1ec1c241d53cdd24b0f62a7d9f89772cb9d4ce2e Mon Sep 17 00:00:00 2001 From: Tobias Schmidt Date: Sat, 20 Aug 2016 17:34:36 -0400 Subject: [PATCH 1/2] Update cAdvisor to d84e075 --- Godeps/Godeps.json | 164 +++++++++--------- .../google/cadvisor/http/handlers.go | 7 +- .../google/cadvisor/metrics/prometheus.go | 131 +++++++------- 3 files changed, 159 insertions(+), 143 deletions(-) diff --git a/Godeps/Godeps.json b/Godeps/Godeps.json index 39b27d7c1cb..66144137ac6 100644 --- a/Godeps/Godeps.json +++ b/Godeps/Godeps.json @@ -1095,208 +1095,208 @@ }, { "ImportPath": "github.com/google/cadvisor/api", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/cache/memory", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/client/v2", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/collector", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/container", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/container/common", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/container/docker", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/container/libcontainer", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/container/raw", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/container/rkt", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/container/systemd", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/devicemapper", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/events", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/fs", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/healthz", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/http", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/http/mux", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/info/v1", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/info/v1/test", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/info/v2", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/machine", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/manager", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/manager/watcher", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/manager/watcher/raw", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/manager/watcher/rkt", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/metrics", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/pages", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/pages/static", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/storage", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/summary", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/utils", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/utils/cloudinfo", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/utils/cpuload", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/utils/cpuload/netlink", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/utils/docker", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/utils/oomparser", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/utils/sysfs", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/utils/sysinfo", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/utils/tail", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/validate", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/cadvisor/version", - "Comment": "v0.23.2-89-g2ed7198", - "Rev": "2ed7198f77395ee9a172878a0a7ab92ab59a2cfd" + "Comment": "v0.24.0-alpha1-1-gd84e075", + "Rev": "d84e0758ab16ee68598702793119c9a7370c1522" }, { "ImportPath": "github.com/google/certificate-transparency/go", diff --git a/vendor/github.com/google/cadvisor/http/handlers.go b/vendor/github.com/google/cadvisor/http/handlers.go index 48e088daff4..420077d7a04 100644 --- a/vendor/github.com/google/cadvisor/http/handlers.go +++ b/vendor/github.com/google/cadvisor/http/handlers.go @@ -89,8 +89,11 @@ func RegisterHandlers(mux httpmux.Mux, containerManager manager.Manager, httpAut return nil } -func RegisterPrometheusHandler(mux httpmux.Mux, containerManager manager.Manager, prometheusEndpoint string, containerNameToLabelsFunc metrics.ContainerNameToLabelsFunc) { - collector := metrics.NewPrometheusCollector(containerManager, containerNameToLabelsFunc) +// RegisterPrometheusHandler creates a new PrometheusCollector, registers it +// on the global registry and configures the provided HTTP mux to handle the +// given Prometheus endpoint. +func RegisterPrometheusHandler(mux httpmux.Mux, containerManager manager.Manager, prometheusEndpoint string, f metrics.ContainerLabelsFunc) { + collector := metrics.NewPrometheusCollector(containerManager, f) prometheus.MustRegister(collector) mux.Handle(prometheusEndpoint, prometheus.Handler()) } diff --git a/vendor/github.com/google/cadvisor/metrics/prometheus.go b/vendor/github.com/google/cadvisor/metrics/prometheus.go index 0e7e8fba0bf..7d738599327 100644 --- a/vendor/github.com/google/cadvisor/metrics/prometheus.go +++ b/vendor/github.com/google/cadvisor/metrics/prometheus.go @@ -25,13 +25,14 @@ import ( "github.com/prometheus/client_golang/prometheus" ) -// This will usually be manager.Manager, but can be swapped out for testing. +// infoProvider will usually be manager.Manager, but can be swapped out for testing. type infoProvider interface { - // Get information about all subcontainers of the specified container (includes self). + // SubcontainersInfo provides information about all subcontainers of the + // specified container including itself. SubcontainersInfo(containerName string, query *info.ContainerInfoRequest) ([]*info.ContainerInfo, error) - // Get information about the version. + // GetVersionInfo provides information about the version. GetVersionInfo() (*info.VersionInfo, error) - // Get information about the machine. + // GetMachineInfo provides information about the machine. GetMachineInfo() (*info.MachineInfo, error) } @@ -56,8 +57,8 @@ func fsValues(fsStats []info.FsStats, valueFn func(*info.FsStats) float64) metri return values } -// A containerMetric describes a multi-dimensional metric used for exposing -// a certain type of container statistic. +// containerMetric describes a multi-dimensional metric used for exposing a +// certain type of container statistic. type containerMetric struct { name string help string @@ -71,21 +72,29 @@ func (cm *containerMetric) desc(baseLabels []string) *prometheus.Desc { return prometheus.NewDesc(cm.name, cm.help, append(baseLabels, cm.extraLabels...), nil) } -type ContainerNameToLabelsFunc func(containerName string) map[string]string +// ContainerLabelsFunc defines all base labels and their values attached to +// each metric exported by cAdvisor. +type ContainerLabelsFunc func(*info.ContainerInfo) map[string]string // PrometheusCollector implements prometheus.Collector. type PrometheusCollector struct { - infoProvider infoProvider - errors prometheus.Gauge - containerMetrics []containerMetric - containerNameToLabels ContainerNameToLabelsFunc + infoProvider infoProvider + errors prometheus.Gauge + containerMetrics []containerMetric + containerLabelsFunc ContainerLabelsFunc } -// NewPrometheusCollector returns a new PrometheusCollector. -func NewPrometheusCollector(infoProvider infoProvider, f ContainerNameToLabelsFunc) *PrometheusCollector { +// NewPrometheusCollector returns a new PrometheusCollector. The passed +// ContainerLabelsFunc specifies which base labels will be attached to all +// exported metrics. If left to nil, the DefaultContainerLabels function +// will be used instead. +func NewPrometheusCollector(i infoProvider, f ContainerLabelsFunc) *PrometheusCollector { + if f == nil { + f = DefaultContainerLabels + } c := &PrometheusCollector{ - infoProvider: infoProvider, - containerNameToLabels: f, + infoProvider: i, + containerLabelsFunc: f, errors: prometheus.NewGauge(prometheus.GaugeOpts{ Namespace: "container", Name: "scrape_error", @@ -533,10 +542,38 @@ func (c *PrometheusCollector) Collect(ch chan<- prometheus.Metric) { } const ( - containerLabelPrefix = "container_label_" - containerEnvPrefix = "container_env_" + // ContainerLabelPrefix is the prefix added to all container labels. + ContainerLabelPrefix = "container_label_" + // ContainerEnvPrefix is the prefix added to all env variable labels. + ContainerEnvPrefix = "container_env_" + // LabelID is the name of the id label. + LabelID = "id" + // LabelName is the name of the name label. + LabelName = "name" + // LabelImage is the name of the image label. + LabelImage = "image" ) +// DefaultContainerLabels implements ContainerLabelsFunc. It exports the +// container name, first alias, image name as well as all its env and label +// values. +func DefaultContainerLabels(container *info.ContainerInfo) map[string]string { + set := map[string]string{LabelID: container.Name} + if len(container.Aliases) > 0 { + set[LabelName] = container.Aliases[0] + } + if image := container.Spec.Image; len(image) > 0 { + set[LabelImage] = image + } + for k, v := range container.Spec.Labels { + set[ContainerLabelPrefix+k] = v + } + for k, v := range container.Spec.Envs { + set[ContainerEnvPrefix+k] = v + } + return set +} + func (c *PrometheusCollector) collectContainersInfo(ch chan<- prometheus.Metric) { containers, err := c.infoProvider.SubcontainersInfo("/", &info.ContainerInfoRequest{NumStats: 1}) if err != nil { @@ -545,56 +582,32 @@ func (c *PrometheusCollector) collectContainersInfo(ch chan<- prometheus.Metric) return } for _, container := range containers { - baseLabels := []string{"id"} - id := container.Name - name := id - if len(container.Aliases) > 0 { - name = container.Aliases[0] - baseLabels = append(baseLabels, "name") - } - image := container.Spec.Image - if len(image) > 0 { - baseLabels = append(baseLabels, "image") - } - baseLabelValues := []string{id, name, image}[:len(baseLabels)] - - if c.containerNameToLabels != nil { - newLabels := c.containerNameToLabels(name) - for k, v := range newLabels { - baseLabels = append(baseLabels, sanitizeLabelName(k)) - baseLabelValues = append(baseLabelValues, v) - } - } - - for k, v := range container.Spec.Labels { - baseLabels = append(baseLabels, sanitizeLabelName(containerLabelPrefix+k)) - baseLabelValues = append(baseLabelValues, v) - } - for k, v := range container.Spec.Envs { - baseLabels = append(baseLabels, sanitizeLabelName(containerEnvPrefix+k)) - baseLabelValues = append(baseLabelValues, v) + labels, values := []string{}, []string{} + for l, v := range c.containerLabelsFunc(container) { + labels = append(labels, sanitizeLabelName(l)) + values = append(values, v) } // Container spec - desc := prometheus.NewDesc("container_start_time_seconds", "Start time of the container since unix epoch in seconds.", baseLabels, nil) - ch <- prometheus.MustNewConstMetric(desc, prometheus.GaugeValue, float64(container.Spec.CreationTime.Unix()), baseLabelValues...) + desc := prometheus.NewDesc("container_start_time_seconds", "Start time of the container since unix epoch in seconds.", labels, nil) + ch <- prometheus.MustNewConstMetric(desc, prometheus.GaugeValue, float64(container.Spec.CreationTime.Unix()), values...) if container.Spec.HasCpu { - desc = prometheus.NewDesc("container_spec_cpu_period", "CPU period of the container.", baseLabels, nil) - ch <- prometheus.MustNewConstMetric(desc, prometheus.GaugeValue, float64(container.Spec.Cpu.Period), baseLabelValues...) + desc = prometheus.NewDesc("container_spec_cpu_period", "CPU period of the container.", labels, nil) + ch <- prometheus.MustNewConstMetric(desc, prometheus.GaugeValue, float64(container.Spec.Cpu.Period), values...) if container.Spec.Cpu.Quota != 0 { - desc = prometheus.NewDesc("container_spec_cpu_quota", "CPU quota of the container.", baseLabels, nil) - ch <- prometheus.MustNewConstMetric(desc, prometheus.GaugeValue, float64(container.Spec.Cpu.Quota), baseLabelValues...) + desc = prometheus.NewDesc("container_spec_cpu_quota", "CPU quota of the container.", labels, nil) + ch <- prometheus.MustNewConstMetric(desc, prometheus.GaugeValue, float64(container.Spec.Cpu.Quota), values...) } - desc := prometheus.NewDesc("container_spec_cpu_shares", "CPU share of the container.", baseLabels, nil) - ch <- prometheus.MustNewConstMetric(desc, prometheus.GaugeValue, float64(container.Spec.Cpu.Limit), baseLabelValues...) + desc := prometheus.NewDesc("container_spec_cpu_shares", "CPU share of the container.", labels, nil) + ch <- prometheus.MustNewConstMetric(desc, prometheus.GaugeValue, float64(container.Spec.Cpu.Limit), values...) } if container.Spec.HasMemory { - desc := prometheus.NewDesc("container_spec_memory_limit_bytes", "Memory limit for the container.", baseLabels, nil) - ch <- prometheus.MustNewConstMetric(desc, prometheus.GaugeValue, specMemoryValue(container.Spec.Memory.Limit), baseLabelValues...) - desc = prometheus.NewDesc("container_spec_memory_swap_limit_bytes", "Memory swap limit for the container.", baseLabels, nil) - ch <- prometheus.MustNewConstMetric(desc, prometheus.GaugeValue, specMemoryValue(container.Spec.Memory.SwapLimit), baseLabelValues...) + desc := prometheus.NewDesc("container_spec_memory_limit_bytes", "Memory limit for the container.", labels, nil) + ch <- prometheus.MustNewConstMetric(desc, prometheus.GaugeValue, specMemoryValue(container.Spec.Memory.Limit), values...) + desc = prometheus.NewDesc("container_spec_memory_swap_limit_bytes", "Memory swap limit for the container.", labels, nil) + ch <- prometheus.MustNewConstMetric(desc, prometheus.GaugeValue, specMemoryValue(container.Spec.Memory.SwapLimit), values...) } // Now for the actual metrics @@ -603,9 +616,9 @@ func (c *PrometheusCollector) collectContainersInfo(ch chan<- prometheus.Metric) if cm.condition != nil && !cm.condition(container.Spec) { continue } - desc := cm.desc(baseLabels) + desc := cm.desc(labels) for _, metricValue := range cm.getValues(stats) { - ch <- prometheus.MustNewConstMetric(desc, cm.valueType, float64(metricValue.value), append(baseLabelValues, metricValue.labels...)...) + ch <- prometheus.MustNewConstMetric(desc, cm.valueType, float64(metricValue.value), append(values, metricValue.labels...)...) } } } From 12c248315f8191396574085591e1d749ab0fe670 Mon Sep 17 00:00:00 2001 From: Tobias Schmidt Date: Sat, 20 Aug 2016 18:04:34 -0400 Subject: [PATCH 2/2] Filter internal Kubernetes labels from Prometheus metrics Kubernetes uses Docker labels as storage for some internal labels. The majority of these labels are not meaningful metric labels and a few of them are even harmful as they're not static and cause wrong aggregation results. This change provides a custom labels func to only attach meaningful labels to cAdvisor exported metrics. --- pkg/kubelet/cadvisor/cadvisor_linux.go | 26 ++++++++- pkg/kubelet/cadvisor/cadvisor_linux_test.go | 65 +++++++++++++++++++++ 2 files changed, 89 insertions(+), 2 deletions(-) create mode 100644 pkg/kubelet/cadvisor/cadvisor_linux_test.go diff --git a/pkg/kubelet/cadvisor/cadvisor_linux.go b/pkg/kubelet/cadvisor/cadvisor_linux.go index c7b381700a4..853e0d5d566 100644 --- a/pkg/kubelet/cadvisor/cadvisor_linux.go +++ b/pkg/kubelet/cadvisor/cadvisor_linux.go @@ -33,7 +33,9 @@ import ( cadvisorapi "github.com/google/cadvisor/info/v1" cadvisorapiv2 "github.com/google/cadvisor/info/v2" "github.com/google/cadvisor/manager" + "github.com/google/cadvisor/metrics" "github.com/google/cadvisor/utils/sysfs" + "k8s.io/kubernetes/pkg/kubelet/types" "k8s.io/kubernetes/pkg/util/runtime" ) @@ -70,7 +72,27 @@ func init() { } } -// Creates a cAdvisor and exports its API on the specified port if port > 0. +func containerLabels(c *cadvisorapi.ContainerInfo) map[string]string { + set := map[string]string{metrics.LabelID: c.Name} + if len(c.Aliases) > 0 { + set[metrics.LabelName] = c.Aliases[0] + } + if image := c.Spec.Image; len(image) > 0 { + set[metrics.LabelImage] = image + } + if v, ok := c.Spec.Labels[types.KubernetesPodNameLabel]; ok { + set["pod_name"] = v + } + if v, ok := c.Spec.Labels[types.KubernetesPodNamespaceLabel]; ok { + set["namespace"] = v + } + if v, ok := c.Spec.Labels[types.KubernetesContainerNameLabel]; ok { + set["container_name"] = v + } + return set +} + +// New creates a cAdvisor and exports its API on the specified port if port > 0. func New(port uint, runtime string) (Interface, error) { sysFs, err := sysfs.NewRealSysFs() if err != nil { @@ -108,7 +130,7 @@ func (cc *cadvisorClient) exportHTTP(port uint) error { return err } - cadvisorhttp.RegisterPrometheusHandler(mux, cc, "/metrics", nil) + cadvisorhttp.RegisterPrometheusHandler(mux, cc, "/metrics", containerLabels) // Only start the http server if port > 0 if port > 0 { diff --git a/pkg/kubelet/cadvisor/cadvisor_linux_test.go b/pkg/kubelet/cadvisor/cadvisor_linux_test.go new file mode 100644 index 00000000000..48f06e026c1 --- /dev/null +++ b/pkg/kubelet/cadvisor/cadvisor_linux_test.go @@ -0,0 +1,65 @@ +// +build cgo,linux + +/* +Copyright 2016 The Kubernetes Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +package cadvisor + +import ( + "reflect" + "testing" + + info "github.com/google/cadvisor/info/v1" + "github.com/google/cadvisor/metrics" + "k8s.io/kubernetes/pkg/kubelet/types" +) + +func TestContainerLabels(t *testing.T) { + container := &info.ContainerInfo{ + ContainerReference: info.ContainerReference{ + Name: "/docker/f81ad5335d390944e454ea19ab0924037d57337c19731524ad96eb26e74b6c6d", + Aliases: []string{"k8s_POD.639b2af2_foo-web-315473031-e40e2_foobar_a369ace2-5fa9-11e6-b10f-c81f66e5e84d_851a97fd"}, + }, + Spec: info.ContainerSpec{ + Image: "qux/foo:latest", + Labels: map[string]string{ + "io.kubernetes.container.hash": "639b2af2", + types.KubernetesContainerNameLabel: "POD", + "io.kubernetes.container.restartCount": "0", + "io.kubernetes.container.terminationMessagePath": "", + types.KubernetesPodNameLabel: "foo-web-315473031-e40e2", + types.KubernetesPodNamespaceLabel: "foobar", + "io.kubernetes.pod.terminationGracePeriod": "30", + types.KubernetesPodUIDLabel: "a369ace2-5fa9-11e6-b10f-c81f66e5e84d", + }, + Envs: map[string]string{ + "foo+env": "prod", + }, + }, + } + want := map[string]string{ + metrics.LabelID: "/docker/f81ad5335d390944e454ea19ab0924037d57337c19731524ad96eb26e74b6c6d", + metrics.LabelName: "k8s_POD.639b2af2_foo-web-315473031-e40e2_foobar_a369ace2-5fa9-11e6-b10f-c81f66e5e84d_851a97fd", + metrics.LabelImage: "qux/foo:latest", + "namespace": "foobar", + "container_name": "POD", + "pod_name": "foo-web-315473031-e40e2", + } + + if have := containerLabels(container); !reflect.DeepEqual(want, have) { + t.Errorf("want %v, have %v", want, have) + } +}