// GetMetricTypes returns list of available metrics func (d *docker) GetMetricTypes(_ plugin.ConfigType) ([]plugin.MetricType, error) { var metricTypes []plugin.MetricType var err error // initialize containerData struct data := containerData{ Stats: wrapper.NewStatistics(), } // generate available namespace for data container structure dockerMetrics := []string{} utils.FromCompositeObject(data, "", &dockerMetrics) nscreator := nsCreator{dynamicElements: definedDynamicElements} for _, metricName := range dockerMetrics { ns := core.NewNamespace(NS_VENDOR, NS_PLUGIN). AddDynamicElement("docker_id", "an id of docker container") if ns, err = nscreator.createMetricNamespace(ns, metricName); err != nil { // skip this metric name which is not supported // fmt.Fprintf(os.Stderr, "Error in creating metric namespace: %v\n", err) continue } metricType := plugin.MetricType{ Namespace_: ns, Version_: VERSION, } metricTypes = append(metricTypes, metricType) } return metricTypes, nil }
// Recursively traverse the Executor struct, building "/"-delimited strings that resemble snap metric types. If a given // feature is not enabled on a Mesos agent (e.g. the network isolator), then those metrics will be removed from the // metric types returned by this function. func GetMonitoringStatisticsMetricTypes(host string) ([]string, error) { log.Debug("Getting monitoring statistics metrics type from host ", host) // TODO(roger): supporting NetTrafficControlStatistics means adding another dynamic metric to the plugin. // When we're ready to do this, remove ns.InspectEmptyContainers(ns.AlwaysFalse) so this defaults to true. namespaces := []string{} err := ns.FromCompositeObject( &mesos_pb2.ResourceStatistics{}, "", &namespaces, ns.InspectEmptyContainers(ns.AlwaysFalse)) if err != nil { log.Error(err) return nil, err } // Avoid returning a metric type that is impossible to collect on this system flags, err := GetFlags(host) if err != nil { log.Error(err) return nil, err } // Isolators are defined using a comma-separated string passed to the "--isolation" flag on the Mesos agent. // See https://github.com/apache/mesos/blob/0.28.1/src/slave/containerizer/mesos/containerizer.cpp#L196-L223 isolators := strings.Split(flags["isolation"], ",") if str.Contains(isolators, "cgroups/perf_event") { log.Debug("Isolator cgroups/perf_event is enabled on host ", host) // Expects a perf event from the output of `perf list`. Mesos then normalizes the event name. See // https://github.com/apache/mesos/blob/0.28.1/src/linux/perf.cpp#L65-L71 namespaces = deleteFromSlice(namespaces, "^perf/.*") var normalizedPerfEvents []string perfEvents := strings.Split(flags["perf_events"], ",") for _, event := range perfEvents { log.Debug("Adding perf event ", event, " to metrics catalog") event = fmt.Sprintf("perf/%s", normalizePerfEventName(event)) normalizedPerfEvents = append(normalizedPerfEvents, event) } namespaces = append(namespaces, normalizedPerfEvents...) } else { log.Debug("Isolator cgroups/perf_event is not enabled on host ", host) namespaces = deleteFromSlice(namespaces, "^perf.*") } if !str.Contains(isolators, "posix/disk") { log.Debug("Isolator posix/disk is not enabled on host ", host) namespaces = deleteFromSlice(namespaces, "^disk_.*") } if !str.Contains(isolators, "network/port_mapping") { log.Debug("Isolator network/port_mapping is not enabled on host ", host) namespaces = deleteFromSlice(namespaces, "^net_.*") } return namespaces, nil }
// Recursively traverse the Frameworks struct, building "/"-delimited strings that resemble snap metric types. func GetFrameworksMetricTypes() ([]string, error) { log.Debug("Getting frameworks metric types from protobuf (mesos_pb2)") namespaces := []string{} if err := ns.FromCompositeObject(Framework{}, "", &namespaces); err != nil { log.Error(err) return nil, err } for i := 0; i < len(namespaces); i++ { if namespaces[i] == "id" { namespaces = append(namespaces[:i], namespaces[i+1:]...) break } } return namespaces, nil }